Search moodle.org's
Developer Documentation

See Release Notes
Long Term Support Release

  • Bug fixes for general core bugs in 3.9.x will end* 10 May 2021 (12 months).
  • Bug fixes for security issues in 3.9.x will end* 8 May 2023 (36 months).
  • PHP version: minimum PHP 7.2.0 Note: minimum PHP version has increased since Moodle 3.8. PHP 7.3.x and 7.4.x are supported too.

Differences Between: [Versions 39 and 310] [Versions 39 and 311] [Versions 39 and 400] [Versions 39 and 401] [Versions 39 and 402] [Versions 39 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   * Test course_enrolment_manager parts.
  19   *
  20   * @package    core_enrol
  21   * @category   test
  22   * @copyright  2016 Ruslan Kabalin, Lancaster University
  23   * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
  24   */
  25  
  26  defined('MOODLE_INTERNAL') || die();
  27  
  28  
  29  /**
  30   * Test course_enrolment_manager parts.
  31   *
  32   * @package    core
  33   * @category   test
  34   * @copyright  2016 Ruslan Kabalin, Lancaster University
  35   * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
  36   * @covers     \course_enrolment_manager
  37   */
  38  class core_course_enrolment_manager_testcase extends advanced_testcase {
  39      /**
  40       * The course used in tests.
  41       * @var stdClass
  42       */
  43      private $course = null;
  44      /**
  45       * List of users used in tests.
  46       * @var array
  47       */
  48      private $users = array();
  49      /**
  50       * List of groups used in tests.
  51       * @var array
  52       */
  53      private $groups = array();
  54  
  55      /**
  56       * Tests set up
  57       */
  58      protected function setUp() {
  59          global $CFG;
  60          require_once($CFG->dirroot . '/enrol/locallib.php');
  61          $this->setAdminUser();
  62  
  63          $users = array();
  64          $groups = array();
  65          // Create the course and the users.
  66          $course = $this->getDataGenerator()->create_course();
  67          $users['user0'] = $this->getDataGenerator()->create_user(
  68                  array('username' => 'user0', 'firstname' => 'user0')); // A user without group.
  69          $users['user1'] = $this->getDataGenerator()->create_user(
  70                  array('username' => 'user1', 'firstname' => 'user1')); // User for group 1.
  71          $users['user21'] = $this->getDataGenerator()->create_user(
  72                  array('username' => 'user21', 'firstname' => 'user21')); // Two users for group 2.
  73          $users['user22'] = $this->getDataGenerator()->create_user(
  74                  array('username' => 'user22', 'firstname' => 'user22'));
  75          $users['userall'] = $this->getDataGenerator()->create_user(
  76                  array('username' => 'userall', 'firstname' => 'userall')); // A user in all groups.
  77          $users['usertch'] = $this->getDataGenerator()->create_user(
  78                  array('username' => 'usertch', 'firstname' => 'usertch')); // A user with teacher role.
  79  
  80          // Enrol the users in the course.
  81          $this->getDataGenerator()->enrol_user($users['user0']->id, $course->id, 'student'); // Student.
  82          $this->getDataGenerator()->enrol_user($users['user1']->id, $course->id, 'student'); // Student.
  83          $this->getDataGenerator()->enrol_user($users['user21']->id, $course->id, 'student'); // Student.
  84          $this->getDataGenerator()->enrol_user($users['user22']->id, $course->id, 'student', 'manual', 0, 0, ENROL_USER_SUSPENDED); // Suspended student.
  85          $this->getDataGenerator()->enrol_user($users['userall']->id, $course->id, 'student'); // Student.
  86          $this->getDataGenerator()->enrol_user($users['usertch']->id, $course->id, 'editingteacher'); // Teacher.
  87  
  88          // Create 2 groups.
  89          $groups['group1'] = $this->getDataGenerator()->create_group(array('courseid' => $course->id));
  90          $groups['group2'] = $this->getDataGenerator()->create_group(array('courseid' => $course->id));
  91  
  92          // Add the users to the groups.
  93          $this->getDataGenerator()->create_group_member(
  94                  array('groupid' => $groups['group1']->id, 'userid' => $users['user1']->id));
  95          $this->getDataGenerator()->create_group_member(
  96                  array('groupid' => $groups['group2']->id, 'userid' => $users['user21']->id));
  97          $this->getDataGenerator()->create_group_member(
  98                  array('groupid' => $groups['group2']->id, 'userid' => $users['user22']->id));
  99          $this->getDataGenerator()->create_group_member(
 100                  array('groupid' => $groups['group1']->id, 'userid' => $users['userall']->id));
 101          $this->getDataGenerator()->create_group_member(
 102                  array('groupid' => $groups['group2']->id, 'userid' => $users['userall']->id));
 103  
 104          // Make setup data accessible from test methods.
 105          $this->course = $course;
 106          $this->users = $users;
 107          $this->groups = $groups;
 108  
 109          // Make sample users and not enroll to any course.
 110          $this->getDataGenerator()->create_user([
 111                  'username' => 'testapiuser1',
 112                  'firstname' => 'testapiuser 1'
 113          ]);
 114          $this->getDataGenerator()->create_user([
 115                  'username' => 'testapiuser2',
 116                  'firstname' => 'testapiuser 2'
 117          ]);
 118          $this->getDataGenerator()->create_user([
 119                  'username' => 'testapiuser3',
 120                  'firstname' => 'testapiuser 3'
 121          ]);
 122      }
 123  
 124      /**
 125       * Verify get_total_users() returned number of users expected in every situation.
 126       */
 127      public function test_get_total_users() {
 128          global $PAGE;
 129  
 130          $this->resetAfterTest();
 131  
 132          // All users filtering.
 133          $manager = new course_enrolment_manager($PAGE, $this->course);
 134          $totalusers = $manager->get_total_users();
 135          $this->assertEquals(6, $totalusers, 'All users must be returned when no filtering is applied.');
 136  
 137          // Student role filtering.
 138          $manager = new course_enrolment_manager($PAGE, $this->course, null, 5);
 139          $totalusers = $manager->get_total_users();
 140          $this->assertEquals(5, $totalusers, 'Only students must be returned when student role filtering is applied.');
 141  
 142          // Teacher role filtering.
 143          $manager = new course_enrolment_manager($PAGE, $this->course, null, 3);
 144          $totalusers = $manager->get_total_users();
 145          $this->assertEquals(1, $totalusers, 'Only teacher must be returned when teacher role filtering is applied.');
 146  
 147          // Search user filtering.
 148          $manager = new course_enrolment_manager($PAGE, $this->course, null, 0, 'userall');
 149          $totalusers = $manager->get_total_users();
 150          $this->assertEquals(1, $totalusers, 'Only searchable user must be returned when search filtering is applied.');
 151  
 152          // Group 1 filtering.
 153          $manager = new course_enrolment_manager($PAGE, $this->course, null, 0, '', $this->groups['group1']->id);
 154          $totalusers = $manager->get_total_users();
 155          $this->assertEquals(2, $totalusers, 'Only group members must be returned when group filtering is applied.');
 156  
 157          // Group 2 filtering.
 158          $manager = new course_enrolment_manager($PAGE, $this->course, null, 0, '', $this->groups['group2']->id);
 159          $totalusers = $manager->get_total_users();
 160          $this->assertEquals(3, $totalusers, 'Only group members must be returned when group filtering is applied.');
 161  
 162          // 'No groups' filtering.
 163          $manager = new course_enrolment_manager($PAGE, $this->course, null, 0, '', -1);
 164          $totalusers = $manager->get_total_users();
 165          $this->assertEquals(2, $totalusers, 'Only non-group members must be returned when \'no groups\' filtering is applied.');
 166  
 167          // Active users filtering.
 168          $manager = new course_enrolment_manager($PAGE, $this->course, null, 0, '', 0, ENROL_USER_ACTIVE);
 169          $totalusers = $manager->get_total_users();
 170          $this->assertEquals(5, $totalusers, 'Only active users must be returned when active users filtering is applied.');
 171  
 172          // Suspended users filtering.
 173          $manager = new course_enrolment_manager($PAGE, $this->course, null, 0, '', 0, ENROL_USER_SUSPENDED);
 174          $totalusers = $manager->get_total_users();
 175          $this->assertEquals(1, $totalusers, 'Only suspended users must be returned when suspended users filtering is applied.');
 176      }
 177  
 178      /**
 179       * Verify get_users() returned number of users expected in every situation.
 180       */
 181      public function test_get_users() {
 182          global $PAGE;
 183  
 184          $this->resetAfterTest();
 185  
 186          // All users filtering.
 187          $manager = new course_enrolment_manager($PAGE, $this->course);
 188          $users = $manager->get_users('id');
 189          $this->assertCount(6, $users,  'All users must be returned when no filtering is applied.');
 190          $this->assertArrayHasKey($this->users['user0']->id, $users);
 191          $this->assertArrayHasKey($this->users['user1']->id, $users);
 192          $this->assertArrayHasKey($this->users['user21']->id, $users);
 193          $this->assertArrayHasKey($this->users['user22']->id, $users);
 194          $this->assertArrayHasKey($this->users['userall']->id, $users);
 195          $this->assertArrayHasKey($this->users['usertch']->id, $users);
 196  
 197          // Student role filtering.
 198          $manager = new course_enrolment_manager($PAGE, $this->course, null, 5);
 199          $users = $manager->get_users('id');
 200          $this->assertCount(5, $users, 'Only students must be returned when student role filtering is applied.');
 201          $this->assertArrayHasKey($this->users['user0']->id, $users);
 202          $this->assertArrayHasKey($this->users['user1']->id, $users);
 203          $this->assertArrayHasKey($this->users['user21']->id, $users);
 204          $this->assertArrayHasKey($this->users['user22']->id, $users);
 205          $this->assertArrayHasKey($this->users['userall']->id, $users);
 206  
 207          // Teacher role filtering.
 208          $manager = new course_enrolment_manager($PAGE, $this->course, null, 3);
 209          $users = $manager->get_users('id');
 210          $this->assertCount(1, $users, 'Only teacher must be returned when teacher role filtering is applied.');
 211          $this->assertArrayHasKey($this->users['usertch']->id, $users);
 212  
 213          // Search user filtering.
 214          $manager = new course_enrolment_manager($PAGE, $this->course, null, 0, 'userall');
 215          $users = $manager->get_users('id');
 216          $this->assertCount(1, $users, 'Only searchable user must be returned when search filtering is applied.');
 217          $this->assertArrayHasKey($this->users['userall']->id, $users);
 218  
 219          // Group 1 filtering.
 220          $manager = new course_enrolment_manager($PAGE, $this->course, null, 0, '', $this->groups['group1']->id);
 221          $users = $manager->get_users('id');
 222          $this->assertCount(2, $users, 'Only group members must be returned when group filtering is applied.');
 223          $this->assertArrayHasKey($this->users['user1']->id, $users);
 224          $this->assertArrayHasKey($this->users['userall']->id, $users);
 225  
 226          // Group 2 filtering.
 227          $manager = new course_enrolment_manager($PAGE, $this->course, null, 0, '', $this->groups['group2']->id);
 228          $users = $manager->get_users('id');
 229          $this->assertCount(3, $users, 'Only group members must be returned when group filtering is applied.');
 230          $this->assertArrayHasKey($this->users['user21']->id, $users);
 231          $this->assertArrayHasKey($this->users['user22']->id, $users);
 232          $this->assertArrayHasKey($this->users['userall']->id, $users);
 233  
 234          // 'No groups' filtering.
 235          $manager = new course_enrolment_manager($PAGE, $this->course, null, 0, '', -1);
 236          $users = $manager->get_users('id');
 237          $this->assertCount(2, $users, 'Only non-group members must be returned when \'no groups\' filtering is applied.');
 238          $this->assertArrayHasKey($this->users['user0']->id, $users);
 239          $this->assertArrayHasKey($this->users['usertch']->id, $users);
 240  
 241          // Active users filtering.
 242          $manager = new course_enrolment_manager($PAGE, $this->course, null, 0, '', 0, ENROL_USER_ACTIVE);
 243          $users = $manager->get_users('id');
 244          $this->assertCount(5, $users, 'Only active users must be returned when active users filtering is applied.');
 245          $this->assertArrayHasKey($this->users['user0']->id, $users);
 246          $this->assertArrayHasKey($this->users['user1']->id, $users);
 247          $this->assertArrayHasKey($this->users['user21']->id, $users);
 248          $this->assertArrayHasKey($this->users['userall']->id, $users);
 249          $this->assertArrayHasKey($this->users['usertch']->id, $users);
 250  
 251          // Suspended users filtering.
 252          $manager = new course_enrolment_manager($PAGE, $this->course, null, 0, '', 0, ENROL_USER_SUSPENDED);
 253          $users = $manager->get_users('id');
 254          $this->assertCount(1, $users, 'Only suspended users must be returned when suspended users filtering is applied.');
 255          $this->assertArrayHasKey($this->users['user22']->id, $users);
 256      }
 257  
 258      /**
 259       * Test get_potential_users without returnexactcount param.
 260       *
 261       * @dataProvider search_users_provider
 262       *
 263       * @param int $perpage Number of users per page.
 264       * @param bool $returnexactcount Return the exact count or not.
 265       * @param int $expectedusers Expected number of users return.
 266       * @param int $expectedtotalusers Expected total of users in database.
 267       * @param bool $expectedmoreusers Expected for more users return or not.
 268       */
 269      public function test_get_potential_users($perpage, $returnexactcount, $expectedusers, $expectedtotalusers, $expectedmoreusers) {
 270          global $DB, $PAGE;
 271          $this->resetAfterTest();
 272          $this->setAdminUser();
 273  
 274          $enrol = $DB->get_record('enrol', array('courseid' => $this->course->id, 'enrol' => 'manual'));
 275          $manager = new course_enrolment_manager($PAGE, $this->course);
 276          $users = $manager->get_potential_users($enrol->id,
 277                  'testapiuser',
 278                  true,
 279                  0,
 280                  $perpage,
 281                  0,
 282                  $returnexactcount);
 283  
 284          $this->assertCount($expectedusers, $users['users']);
 285          $this->assertEquals($expectedmoreusers, $users['moreusers']);
 286          if ($returnexactcount) {
 287              $this->assertArrayHasKey('totalusers', $users);
 288              $this->assertEquals($expectedtotalusers, $users['totalusers']);
 289          } else {
 290              $this->assertArrayNotHasKey('totalusers', $users);
 291          }
 292      }
 293  
 294      /**
 295       * Test search_other_users with returnexactcount param.
 296       *
 297       * @dataProvider search_users_provider
 298       *
 299       * @param int $perpage Number of users per page.
 300       * @param bool $returnexactcount Return the exact count or not.
 301       * @param int $expectedusers Expected number of users return.
 302       * @param int $expectedtotalusers Expected total of users in database.
 303       * @param bool $expectedmoreusers Expected for more users return or not.
 304       */
 305      public function test_search_other_users($perpage, $returnexactcount, $expectedusers, $expectedtotalusers, $expectedmoreusers) {
 306          global $PAGE;
 307          $this->resetAfterTest();
 308          $this->setAdminUser();
 309  
 310          $manager = new course_enrolment_manager($PAGE, $this->course);
 311          $users = $manager->search_other_users(
 312                  'testapiuser',
 313                  true,
 314                  0,
 315                  $perpage,
 316                  $returnexactcount);
 317  
 318          $this->assertCount($expectedusers, $users['users']);
 319          $this->assertEquals($expectedmoreusers, $users['moreusers']);
 320          if ($returnexactcount) {
 321              $this->assertArrayHasKey('totalusers', $users);
 322              $this->assertEquals($expectedtotalusers, $users['totalusers']);
 323          } else {
 324              $this->assertArrayNotHasKey('totalusers', $users);
 325          }
 326      }
 327  
 328      /**
 329       * Test case for test_get_potential_users, test_search_other_users and test_search_users tests.
 330       *
 331       * @return array Dataset
 332       */
 333      public function search_users_provider() {
 334          return [
 335                  [2, false, 2, 3, true],
 336                  [5, false, 3, 3, false],
 337                  [2, true, 2, 3, true],
 338                  [5, true, 3, 3, false]
 339          ];
 340      }
 341  
 342      /**
 343       * Test search_users function.
 344       *
 345       * @dataProvider search_users_provider
 346       *
 347       * @param int $perpage Number of users per page.
 348       * @param bool $returnexactcount Return the exact count or not.
 349       * @param int $expectedusers Expected number of users return.
 350       * @param int $expectedtotalusers Expected total of users in database.
 351       * @param bool $expectedmoreusers Expected for more users return or not.
 352       */
 353      public function test_search_users($perpage, $returnexactcount, $expectedusers, $expectedtotalusers, $expectedmoreusers) {
 354          global $PAGE;
 355          $this->resetAfterTest();
 356  
 357          $this->getDataGenerator()->create_and_enrol($this->course, 'student', ['firstname' => 'sutest 1']);
 358          $this->getDataGenerator()->create_and_enrol($this->course, 'student', ['firstname' => 'sutest 2']);
 359          $this->getDataGenerator()->create_and_enrol($this->course, 'student', ['firstname' => 'sutest 3']);
 360  
 361          $manager = new course_enrolment_manager($PAGE, $this->course);
 362          $users = $manager->search_users(
 363              'sutest',
 364              true,
 365              0,
 366              $perpage,
 367              $returnexactcount
 368          );
 369  
 370          $this->assertCount($expectedusers, $users['users']);
 371          $this->assertEquals($expectedmoreusers, $users['moreusers']);
 372          if ($returnexactcount) {
 373              $this->assertArrayHasKey('totalusers', $users);
 374              $this->assertEquals($expectedtotalusers, $users['totalusers']);
 375          } else {
 376              $this->assertArrayNotHasKey('totalusers', $users);
 377          }
 378      }
 379  
 380      /**
 381       * Test that search_users observes course group mode restrictions correctly
 382       */
 383      public function test_search_users_course_groupmode(): void {
 384          global $DB, $PAGE;
 385  
 386          $this->resetAfterTest();
 387  
 388          $teacher = $this->getDataGenerator()->create_and_enrol($this->course, 'teacher');
 389          $this->getDataGenerator()->create_group_member(['groupid' => $this->groups['group1']->id, 'userid' => $teacher->id]);
 390          $this->setUser($teacher);
 391  
 392          $users = (new course_enrolment_manager($PAGE, $this->course))->search_users('', false, 0, 25, true);
 393          $this->assertEqualsCanonicalizing([
 394              $teacher->username,
 395              $this->users['user0']->username,
 396              $this->users['user1']->username,
 397              $this->users['user21']->username,
 398              $this->users['user22']->username,
 399              $this->users['userall']->username,
 400              $this->users['usertch']->username,
 401          ], array_column($users['users'], 'username'));
 402          $this->assertEquals(7, $users['totalusers']);
 403  
 404          // Switch course to separate groups.
 405          $this->course->groupmode = SEPARATEGROUPS;
 406          update_course($this->course);
 407  
 408          $users = (new course_enrolment_manager($PAGE, $this->course))->search_users('', false, 0, 25, true);
 409          $this->assertEqualsCanonicalizing([
 410              $teacher->username,
 411              $this->users['user1']->username,
 412              $this->users['userall']->username,
 413          ], array_column($users['users'], 'username'));
 414          $this->assertEquals(3, $users['totalusers']);
 415  
 416          // Allow teacher to access all groups.
 417          $roleid = $DB->get_field('role', 'id', ['shortname' => 'teacher']);
 418          assign_capability('moodle/site:accessallgroups', CAP_ALLOW, $roleid, context_course::instance($this->course->id)->id);
 419  
 420          $users = (new course_enrolment_manager($PAGE, $this->course))->search_users('', false, 0, 25, true);
 421          $this->assertEqualsCanonicalizing([
 422              $teacher->username,
 423              $this->users['user0']->username,
 424              $this->users['user1']->username,
 425              $this->users['user21']->username,
 426              $this->users['user22']->username,
 427              $this->users['userall']->username,
 428              $this->users['usertch']->username,
 429          ], array_column($users['users'], 'username'));
 430          $this->assertEquals(7, $users['totalusers']);
 431      }
 432  }