[ Index ]

PHP Cross Reference of Unnamed Project

title

Body

[close]

/lib/testing/generator/ -> data_generator.php (source)

   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   * Data generator.
  19   *
  20   * @package    core
  21   * @category   test
  22   * @copyright  2012 Petr Skoda {@link http://skodak.org}
  23   * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
  24   */
  25  
  26  defined('MOODLE_INTERNAL') || die();
  27  
  28  /**
  29   * Data generator class for unit tests and other tools that need to create fake test sites.
  30   *
  31   * @package    core
  32   * @category   test
  33   * @copyright  2012 Petr Skoda {@link http://skodak.org}
  34   * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
  35   */
  36  class testing_data_generator {
  37      /** @var int The number of grade categories created */
  38      protected $gradecategorycounter = 0;
  39      /** @var int The number of grade items created */
  40      protected $gradeitemcounter = 0;
  41      /** @var int The number of grade outcomes created */
  42      protected $gradeoutcomecounter = 0;
  43      protected $usercounter = 0;
  44      protected $categorycount = 0;
  45      protected $cohortcount = 0;
  46      protected $coursecount = 0;
  47      protected $scalecount = 0;
  48      protected $groupcount = 0;
  49      protected $groupingcount = 0;
  50      protected $rolecount = 0;
  51      protected $tagcount = 0;
  52  
  53      /** @var array list of plugin generators */
  54      protected $generators = array();
  55  
  56      /** @var array lis of common last names */
  57      public $lastnames = array(
  58          'Smith', 'Johnson', 'Williams', 'Brown', 'Jones', 'Miller', 'Davis', 'García', 'Rodríguez', 'Wilson',
  59          'Müller', 'Schmidt', 'Schneider', 'Fischer', 'Meyer', 'Weber', 'Schulz', 'Wagner', 'Becker', 'Hoffmann',
  60          'Novák', 'Svoboda', 'Novotný', 'Dvořák', 'Černý', 'Procházková', 'Kučerová', 'Veselá', 'Horáková', 'Němcová',
  61          'Смирнов', 'Иванов', 'Кузнецов', 'Соколов', 'Попов', 'Лебедева', 'Козлова', 'Новикова', 'Морозова', 'Петрова',
  62          '王', '李', '张', '刘', '陈', '楊', '黃', '趙', '吳', '周',
  63          '佐藤', '鈴木', '高橋', '田中', '渡辺', '伊藤', '山本', '中村', '小林', '斎藤',
  64      );
  65  
  66      /** @var array lis of common first names */
  67      public $firstnames = array(
  68          'Jacob', 'Ethan', 'Michael', 'Jayden', 'William', 'Isabella', 'Sophia', 'Emma', 'Olivia', 'Ava',
  69          'Lukas', 'Leon', 'Luca', 'Timm', 'Paul', 'Leonie', 'Leah', 'Lena', 'Hanna', 'Laura',
  70          'Jakub', 'Jan', 'Tomáš', 'Lukáš', 'Matěj', 'Tereza', 'Eliška', 'Anna', 'Adéla', 'Karolína',
  71          'Даниил', 'Максим', 'Артем', 'Иван', 'Александр', 'София', 'Анастасия', 'Дарья', 'Мария', 'Полина',
  72          '伟', '伟', '芳', '伟', '秀英', '秀英', '娜', '秀英', '伟', '敏',
  73          '翔', '大翔', '拓海', '翔太', '颯太', '陽菜', 'さくら', '美咲', '葵', '美羽',
  74      );
  75  
  76      public $loremipsum = <<<EOD
  77  Lorem ipsum dolor sit amet, consectetuer adipiscing elit. Nulla non arcu lacinia neque faucibus fringilla. Vivamus porttitor turpis ac leo. Integer in sapien. Nullam eget nisl. Aliquam erat volutpat. Cras elementum. Mauris suscipit, ligula sit amet pharetra semper, nibh ante cursus purus, vel sagittis velit mauris vel metus. Integer malesuada. Nullam lectus justo, vulputate eget mollis sed, tempor sed magna. Mauris elementum mauris vitae tortor. Aliquam erat volutpat.
  78  Temporibus autem quibusdam et aut officiis debitis aut rerum necessitatibus saepe eveniet ut et voluptates repudiandae sint et molestiae non recusandae. Pellentesque ipsum. Cras pede libero, dapibus nec, pretium sit amet, tempor quis. Aliquam ante. Proin in tellus sit amet nibh dignissim sagittis. Vivamus porttitor turpis ac leo. Duis bibendum, lectus ut viverra rhoncus, dolor nunc faucibus libero, eget facilisis enim ipsum id lacus. In sem justo, commodo ut, suscipit at, pharetra vitae, orci. Aliquam erat volutpat. Nulla est.
  79  Vivamus luctus egestas leo. Aenean fermentum risus id tortor. Mauris dictum facilisis augue. Aliquam erat volutpat. Aliquam ornare wisi eu metus. Aliquam id dolor. Duis condimentum augue id magna semper rutrum. Donec iaculis gravida nulla. Pellentesque ipsum. Etiam dictum tincidunt diam. Quisque tincidunt scelerisque libero. Etiam egestas wisi a erat.
  80  Integer lacinia. Cum sociis natoque penatibus et magnis dis parturient montes, nascetur ridiculus mus. Mauris tincidunt sem sed arcu. Nullam feugiat, turpis at pulvinar vulputate, erat libero tristique tellus, nec bibendum odio risus sit amet ante. Aliquam id dolor. Maecenas sollicitudin. Et harum quidem rerum facilis est et expedita distinctio. Mauris suscipit, ligula sit amet pharetra semper, nibh ante cursus purus, vel sagittis velit mauris vel metus. Nullam dapibus fermentum ipsum. Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Nemo enim ipsam voluptatem quia voluptas sit aspernatur aut odit aut fugit, sed quia consequuntur magni dolores eos qui ratione voluptatem sequi nesciunt. Pellentesque sapien. Duis risus. Mauris elementum mauris vitae tortor. Suspendisse nisl. Integer rutrum, orci vestibulum ullamcorper ultricies, lacus quam ultricies odio, vitae placerat pede sem sit amet enim.
  81  In laoreet, magna id viverra tincidunt, sem odio bibendum justo, vel imperdiet sapien wisi sed libero. Proin pede metus, vulputate nec, fermentum fringilla, vehicula vitae, justo. Nullam justo enim, consectetuer nec, ullamcorper ac, vestibulum in, elit. Quis autem vel eum iure reprehenderit qui in ea voluptate velit esse quam nihil molestiae consequatur, vel illum qui dolorem eum fugiat quo voluptas nulla pariatur? Maecenas lorem. Etiam posuere lacus quis dolor. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos hymenaeos. Curabitur ligula sapien, pulvinar a vestibulum quis, facilisis vel sapien. Nam sed tellus id magna elementum tincidunt. Suspendisse nisl. Vivamus luctus egestas leo. Nulla non arcu lacinia neque faucibus fringilla. Etiam dui sem, fermentum vitae, sagittis id, malesuada in, quam. Etiam dictum tincidunt diam. Etiam commodo dui eget wisi. Nemo enim ipsam voluptatem quia voluptas sit aspernatur aut odit aut fugit, sed quia consequuntur magni dolores eos qui ratione voluptatem sequi nesciunt. Proin pede metus, vulputate nec, fermentum fringilla, vehicula vitae, justo. Duis ante orci, molestie vitae vehicula venenatis, tincidunt ac pede. Pellentesque sapien.
  82  EOD;
  83  
  84      /**
  85       * To be called from data reset code only,
  86       * do not use in tests.
  87       * @return void
  88       */
  89      public function reset() {
  90          $this->usercounter = 0;
  91          $this->categorycount = 0;
  92          $this->coursecount = 0;
  93          $this->scalecount = 0;
  94  
  95          foreach ($this->generators as $generator) {
  96              $generator->reset();
  97          }
  98      }
  99  
 100      /**
 101       * Return generator for given plugin or component.
 102       * @param string $component the component name, e.g. 'mod_forum' or 'core_question'.
 103       * @return component_generator_base or rather an instance of the appropriate subclass.
 104       */
 105      public function get_plugin_generator($component) {
 106          list($type, $plugin) = core_component::normalize_component($component);
 107          $cleancomponent = $type . '_' . $plugin;
 108          if ($cleancomponent != $component) {
 109              debugging("Please specify the component you want a generator for as " .
 110                      "{$cleancomponent}, not {$component}.", DEBUG_DEVELOPER);
 111              $component = $cleancomponent;
 112          }
 113  
 114          if (isset($this->generators[$component])) {
 115              return $this->generators[$component];
 116          }
 117  
 118          $dir = core_component::get_component_directory($component);
 119          $lib = $dir . '/tests/generator/lib.php';
 120          if (!$dir || !is_readable($lib)) {
 121              throw new coding_exception("Component {$component} does not support " .
 122                      "generators yet. Missing tests/generator/lib.php.");
 123          }
 124  
 125          include_once($lib);
 126          $classname = $component . '_generator';
 127  
 128          if (!class_exists($classname)) {
 129              throw new coding_exception("Component {$component} does not support " .
 130                      "data generators yet. Class {$classname} not found.");
 131          }
 132  
 133          $this->generators[$component] = new $classname($this);
 134          return $this->generators[$component];
 135      }
 136  
 137      /**
 138       * Create a test user
 139       * @param array|stdClass $record
 140       * @param array $options
 141       * @return stdClass user record
 142       */
 143      public function create_user($record=null, array $options=null) {
 144          global $DB, $CFG;
 145  
 146          $this->usercounter++;
 147          $i = $this->usercounter;
 148  
 149          $record = (array)$record;
 150  
 151          if (!isset($record['auth'])) {
 152              $record['auth'] = 'manual';
 153          }
 154  
 155          if (!isset($record['firstname']) and !isset($record['lastname'])) {
 156              $country = rand(0, 5);
 157              $firstname = rand(0, 4);
 158              $lastname = rand(0, 4);
 159              $female = rand(0, 1);
 160              $record['firstname'] = $this->firstnames[($country*10) + $firstname + ($female*5)];
 161              $record['lastname'] = $this->lastnames[($country*10) + $lastname + ($female*5)];
 162  
 163          } else if (!isset($record['firstname'])) {
 164              $record['firstname'] = 'Firstname'.$i;
 165  
 166          } else if (!isset($record['lastname'])) {
 167              $record['lastname'] = 'Lastname'.$i;
 168          }
 169  
 170          if (!isset($record['firstnamephonetic'])) {
 171              $firstnamephonetic = rand(0, 59);
 172              $record['firstnamephonetic'] = $this->firstnames[$firstnamephonetic];
 173          }
 174  
 175          if (!isset($record['lastnamephonetic'])) {
 176              $lastnamephonetic = rand(0, 59);
 177              $record['lastnamephonetic'] = $this->lastnames[$lastnamephonetic];
 178          }
 179  
 180          if (!isset($record['middlename'])) {
 181              $middlename = rand(0, 59);
 182              $record['middlename'] = $this->firstnames[$middlename];
 183          }
 184  
 185          if (!isset($record['alternatename'])) {
 186              $alternatename = rand(0, 59);
 187              $record['alternatename'] = $this->firstnames[$alternatename];
 188          }
 189  
 190          if (!isset($record['idnumber'])) {
 191              $record['idnumber'] = '';
 192          }
 193  
 194          if (!isset($record['mnethostid'])) {
 195              $record['mnethostid'] = $CFG->mnet_localhost_id;
 196          }
 197  
 198          if (!isset($record['username'])) {
 199              $record['username'] = 'username'.$i;
 200              $j = 2;
 201              while ($DB->record_exists('user', array('username'=>$record['username'], 'mnethostid'=>$record['mnethostid']))) {
 202                  $record['username'] = 'username'.$i.'_'.$j;
 203                  $j++;
 204              }
 205          }
 206  
 207          if (isset($record['password'])) {
 208              $record['password'] = hash_internal_user_password($record['password']);
 209          } else {
 210              // The auth plugin may not fully support this,
 211              // but it is still better/faster than hashing random stuff.
 212              $record['password'] = AUTH_PASSWORD_NOT_CACHED;
 213          }
 214  
 215          if (!isset($record['email'])) {
 216              $record['email'] = $record['username'].'@example.com';
 217          }
 218  
 219          if (!isset($record['confirmed'])) {
 220              $record['confirmed'] = 1;
 221          }
 222  
 223          if (!isset($record['lang'])) {
 224              $record['lang'] = 'en';
 225          }
 226  
 227          if (!isset($record['maildisplay'])) {
 228              $record['maildisplay'] = $CFG->defaultpreference_maildisplay;
 229          }
 230  
 231          if (!isset($record['mailformat'])) {
 232              $record['mailformat'] = $CFG->defaultpreference_mailformat;
 233          }
 234  
 235          if (!isset($record['maildigest'])) {
 236              $record['maildigest'] = $CFG->defaultpreference_maildigest;
 237          }
 238  
 239          if (!isset($record['autosubscribe'])) {
 240              $record['autosubscribe'] = $CFG->defaultpreference_autosubscribe;
 241          }
 242  
 243          if (!isset($record['trackforums'])) {
 244              $record['trackforums'] = $CFG->defaultpreference_trackforums;
 245          }
 246  
 247          if (!isset($record['deleted'])) {
 248              $record['deleted'] = 0;
 249          }
 250  
 251          if (!isset($record['timecreated'])) {
 252              $record['timecreated'] = time();
 253          }
 254  
 255          $record['timemodified'] = $record['timecreated'];
 256          $record['lastip'] = '0.0.0.0';
 257  
 258          if ($record['deleted']) {
 259              $delname = $record['email'].'.'.time();
 260              while ($DB->record_exists('user', array('username'=>$delname))) {
 261                  $delname++;
 262              }
 263              $record['idnumber'] = '';
 264              $record['email']    = md5($record['username']);
 265              $record['username'] = $delname;
 266              $record['picture']  = 0;
 267          }
 268  
 269          $userid = $DB->insert_record('user', $record);
 270  
 271          if (!$record['deleted']) {
 272              context_user::instance($userid);
 273          }
 274  
 275          $user = $DB->get_record('user', array('id' => $userid), '*', MUST_EXIST);
 276  
 277          if (!$record['deleted'] && isset($record['interests'])) {
 278              require_once($CFG->dirroot . '/user/editlib.php');
 279              if (!is_array($record['interests'])) {
 280                  $record['interests'] = preg_split('/\s*,\s*/', trim($record['interests']), -1, PREG_SPLIT_NO_EMPTY);
 281              }
 282              useredit_update_interests($user, $record['interests']);
 283          }
 284  
 285          return $user;
 286      }
 287  
 288      /**
 289       * Create a test course category
 290       * @param array|stdClass $record
 291       * @param array $options
 292       * @return coursecat course category record
 293       */
 294      public function create_category($record=null, array $options=null) {
 295          global $DB, $CFG;
 296          require_once("$CFG->libdir/coursecatlib.php");
 297  
 298          $this->categorycount++;
 299          $i = $this->categorycount;
 300  
 301          $record = (array)$record;
 302  
 303          if (!isset($record['name'])) {
 304              $record['name'] = 'Course category '.$i;
 305          }
 306  
 307          if (!isset($record['description'])) {
 308              $record['description'] = "Test course category $i\n$this->loremipsum";
 309          }
 310  
 311          if (!isset($record['idnumber'])) {
 312              $record['idnumber'] = '';
 313          }
 314  
 315          return coursecat::create($record);
 316      }
 317  
 318      /**
 319       * Create test cohort.
 320       * @param array|stdClass $record
 321       * @param array $options
 322       * @return stdClass cohort record
 323       */
 324      public function create_cohort($record=null, array $options=null) {
 325          global $DB, $CFG;
 326          require_once("$CFG->dirroot/cohort/lib.php");
 327  
 328          $this->cohortcount++;
 329          $i = $this->cohortcount;
 330  
 331          $record = (array)$record;
 332  
 333          if (!isset($record['contextid'])) {
 334              $record['contextid'] = context_system::instance()->id;
 335          }
 336  
 337          if (!isset($record['name'])) {
 338              $record['name'] = 'Cohort '.$i;
 339          }
 340  
 341          if (!isset($record['idnumber'])) {
 342              $record['idnumber'] = '';
 343          }
 344  
 345          if (!isset($record['description'])) {
 346              $record['description'] = "Test cohort $i\n$this->loremipsum";
 347          }
 348  
 349          if (!isset($record['descriptionformat'])) {
 350              $record['descriptionformat'] = FORMAT_MOODLE;
 351          }
 352  
 353          if (!isset($record['visible'])) {
 354              $record['visible'] = 1;
 355          }
 356  
 357          if (!isset($record['component'])) {
 358              $record['component'] = '';
 359          }
 360  
 361          $id = cohort_add_cohort((object)$record);
 362  
 363          return $DB->get_record('cohort', array('id'=>$id), '*', MUST_EXIST);
 364      }
 365  
 366      /**
 367       * Create a test course
 368       * @param array|stdClass $record
 369       * @param array $options with keys:
 370       *      'createsections'=>bool precreate all sections
 371       * @return stdClass course record
 372       */
 373      public function create_course($record=null, array $options=null) {
 374          global $DB, $CFG;
 375          require_once("$CFG->dirroot/course/lib.php");
 376  
 377          $this->coursecount++;
 378          $i = $this->coursecount;
 379  
 380          $record = (array)$record;
 381  
 382          if (!isset($record['fullname'])) {
 383              $record['fullname'] = 'Test course '.$i;
 384          }
 385  
 386          if (!isset($record['shortname'])) {
 387              $record['shortname'] = 'tc_'.$i;
 388          }
 389  
 390          if (!isset($record['idnumber'])) {
 391              $record['idnumber'] = '';
 392          }
 393  
 394          if (!isset($record['format'])) {
 395              $record['format'] = 'topics';
 396          }
 397  
 398          if (!isset($record['newsitems'])) {
 399              $record['newsitems'] = 0;
 400          }
 401  
 402          if (!isset($record['numsections'])) {
 403              $record['numsections'] = 5;
 404          }
 405  
 406          if (!isset($record['summary'])) {
 407              $record['summary'] = "Test course $i\n$this->loremipsum";
 408          }
 409  
 410          if (!isset($record['summaryformat'])) {
 411              $record['summaryformat'] = FORMAT_MOODLE;
 412          }
 413  
 414          if (!isset($record['category'])) {
 415              $record['category'] = $DB->get_field_select('course_categories', "MIN(id)", "parent=0");
 416          }
 417  
 418          if (isset($record['tags']) && !is_array($record['tags'])) {
 419              $record['tags'] = preg_split('/\s*,\s*/', trim($record['tags']), -1, PREG_SPLIT_NO_EMPTY);
 420          }
 421  
 422          $course = create_course((object)$record);
 423          context_course::instance($course->id);
 424          if (!empty($options['createsections'])) {
 425              if (isset($course->numsections)) {
 426                  course_create_sections_if_missing($course, range(0, $course->numsections));
 427              } else {
 428                  course_create_sections_if_missing($course, 0);
 429              }
 430          }
 431  
 432          return $course;
 433      }
 434  
 435      /**
 436       * Create course section if does not exist yet
 437       * @param array|stdClass $record must contain 'course' and 'section' attributes
 438       * @param array|null $options
 439       * @return stdClass
 440       * @throws coding_exception
 441       */
 442      public function create_course_section($record = null, array $options = null) {
 443          global $DB;
 444  
 445          $record = (array)$record;
 446  
 447          if (empty($record['course'])) {
 448              throw new coding_exception('course must be present in testing_data_generator::create_course_section() $record');
 449          }
 450  
 451          if (!isset($record['section'])) {
 452              throw new coding_exception('section must be present in testing_data_generator::create_course_section() $record');
 453          }
 454  
 455          course_create_sections_if_missing($record['course'], $record['section']);
 456          return get_fast_modinfo($record['course'])->get_section_info($record['section']);
 457      }
 458  
 459      /**
 460       * Create a test block.
 461       *
 462       * The $record passed in becomes the basis for the new row added to the
 463       * block_instances table. You only need to supply the values of interest.
 464       * Any missing values have sensible defaults filled in, and ->blockname will be set based on $blockname.
 465       *
 466       * The $options array provides additional data, not directly related to what
 467       * will be inserted in the block_instance table, which may affect the block
 468       * that is created. The meanings of any data passed here depends on the particular
 469       * type of block being created.
 470       *
 471       * @param string $blockname the type of block to create. E.g. 'html'.
 472       * @param array|stdClass $record forms the basis for the entry to be inserted in the block_instances table.
 473       * @param array $options further, block-specific options to control how the block is created.
 474       * @return stdClass new block_instance record.
 475       */
 476      public function create_block($blockname, $record=null, array $options=array()) {
 477          $generator = $this->get_plugin_generator('block_'.$blockname);
 478          return $generator->create_instance($record, $options);
 479      }
 480  
 481      /**
 482       * Create a test activity module.
 483       *
 484       * The $record should contain the same data that you would call from
 485       * ->get_data() when the mod_[type]_mod_form is submitted, except that you
 486       * only need to supply values of interest. The only required value is
 487       * 'course'. Any missing values will have a sensible default supplied.
 488       *
 489       * The $options array provides additional data, not directly related to what
 490       * would come back from the module edit settings form, which may affect the activity
 491       * that is created. The meanings of any data passed here depends on the particular
 492       * type of activity being created.
 493       *
 494       * @param string $modulename the type of activity to create. E.g. 'forum' or 'quiz'.
 495       * @param array|stdClass $record data, as if from the module edit settings form.
 496       * @param array $options additional data that may affect how the module is created.
 497       * @return stdClass activity record new new record that was just inserted in the table
 498       *      like 'forum' or 'quiz', with a ->cmid field added.
 499       */
 500      public function create_module($modulename, $record=null, array $options=null) {
 501          $generator = $this->get_plugin_generator('mod_'.$modulename);
 502          return $generator->create_instance($record, $options);
 503      }
 504  
 505      /**
 506       * Create a test group for the specified course
 507       *
 508       * $record should be either an array or a stdClass containing infomation about the group to create.
 509       * At the very least it needs to contain courseid.
 510       * Default values are added for name, description, and descriptionformat if they are not present.
 511       *
 512       * This function calls groups_create_group() to create the group within the database.
 513       * @see groups_create_group
 514       * @param array|stdClass $record
 515       * @return stdClass group record
 516       */
 517      public function create_group($record) {
 518          global $DB, $CFG;
 519  
 520          require_once($CFG->dirroot . '/group/lib.php');
 521  
 522          $this->groupcount++;
 523          $i = $this->groupcount;
 524  
 525          $record = (array)$record;
 526  
 527          if (empty($record['courseid'])) {
 528              throw new coding_exception('courseid must be present in testing_data_generator::create_group() $record');
 529          }
 530  
 531          if (!isset($record['name'])) {
 532              $record['name'] = 'group-' . $i;
 533          }
 534  
 535          if (!isset($record['description'])) {
 536              $record['description'] = "Test Group $i\n{$this->loremipsum}";
 537          }
 538  
 539          if (!isset($record['descriptionformat'])) {
 540              $record['descriptionformat'] = FORMAT_MOODLE;
 541          }
 542  
 543          $id = groups_create_group((object)$record);
 544  
 545          return $DB->get_record('groups', array('id'=>$id));
 546      }
 547  
 548      /**
 549       * Create a test group member
 550       * @param array|stdClass $record
 551       * @throws coding_exception
 552       * @return boolean
 553       */
 554      public function create_group_member($record) {
 555          global $DB, $CFG;
 556  
 557          require_once($CFG->dirroot . '/group/lib.php');
 558  
 559          $record = (array)$record;
 560  
 561          if (empty($record['userid'])) {
 562              throw new coding_exception('user must be present in testing_util::create_group_member() $record');
 563          }
 564  
 565          if (!isset($record['groupid'])) {
 566              throw new coding_exception('group must be present in testing_util::create_group_member() $record');
 567          }
 568  
 569          if (!isset($record['component'])) {
 570              $record['component'] = null;
 571          }
 572          if (!isset($record['itemid'])) {
 573              $record['itemid'] = 0;
 574          }
 575  
 576          return groups_add_member($record['groupid'], $record['userid'], $record['component'], $record['itemid']);
 577      }
 578  
 579      /**
 580       * Create a test grouping for the specified course
 581       *
 582       * $record should be either an array or a stdClass containing infomation about the grouping to create.
 583       * At the very least it needs to contain courseid.
 584       * Default values are added for name, description, and descriptionformat if they are not present.
 585       *
 586       * This function calls groups_create_grouping() to create the grouping within the database.
 587       * @see groups_create_grouping
 588       * @param array|stdClass $record
 589       * @return stdClass grouping record
 590       */
 591      public function create_grouping($record) {
 592          global $DB, $CFG;
 593  
 594          require_once($CFG->dirroot . '/group/lib.php');
 595  
 596          $this->groupingcount++;
 597          $i = $this->groupingcount;
 598  
 599          $record = (array)$record;
 600  
 601          if (empty($record['courseid'])) {
 602              throw new coding_exception('courseid must be present in testing_data_generator::create_grouping() $record');
 603          }
 604  
 605          if (!isset($record['name'])) {
 606              $record['name'] = 'grouping-' . $i;
 607          }
 608  
 609          if (!isset($record['description'])) {
 610              $record['description'] = "Test Grouping $i\n{$this->loremipsum}";
 611          }
 612  
 613          if (!isset($record['descriptionformat'])) {
 614              $record['descriptionformat'] = FORMAT_MOODLE;
 615          }
 616  
 617          $id = groups_create_grouping((object)$record);
 618  
 619          return $DB->get_record('groupings', array('id'=>$id));
 620      }
 621  
 622      /**
 623       * Create a test grouping group
 624       * @param array|stdClass $record
 625       * @throws coding_exception
 626       * @return boolean
 627       */
 628      public function create_grouping_group($record) {
 629          global $DB, $CFG;
 630  
 631          require_once($CFG->dirroot . '/group/lib.php');
 632  
 633          $record = (array)$record;
 634  
 635          if (empty($record['groupingid'])) {
 636              throw new coding_exception('grouping must be present in testing::create_grouping_group() $record');
 637          }
 638  
 639          if (!isset($record['groupid'])) {
 640              throw new coding_exception('group must be present in testing_util::create_grouping_group() $record');
 641          }
 642  
 643          return groups_assign_grouping($record['groupingid'], $record['groupid']);
 644      }
 645  
 646      /**
 647       * Create an instance of a repository.
 648       *
 649       * @param string type of repository to create an instance for.
 650       * @param array|stdClass $record data to use to up set the instance.
 651       * @param array $options options
 652       * @return stdClass repository instance record
 653       * @since Moodle 2.5.1
 654       */
 655      public function create_repository($type, $record=null, array $options = null) {
 656          $generator = $this->get_plugin_generator('repository_'.$type);
 657          return $generator->create_instance($record, $options);
 658      }
 659  
 660      /**
 661       * Create an instance of a repository.
 662       *
 663       * @param string type of repository to create an instance for.
 664       * @param array|stdClass $record data to use to up set the instance.
 665       * @param array $options options
 666       * @return repository_type object
 667       * @since Moodle 2.5.1
 668       */
 669      public function create_repository_type($type, $record=null, array $options = null) {
 670          $generator = $this->get_plugin_generator('repository_'.$type);
 671          return $generator->create_type($record, $options);
 672      }
 673  
 674  
 675      /**
 676       * Create a test scale
 677       * @param array|stdClass $record
 678       * @param array $options
 679       * @return stdClass block instance record
 680       */
 681      public function create_scale($record=null, array $options=null) {
 682          global $DB;
 683  
 684          $this->scalecount++;
 685          $i = $this->scalecount;
 686  
 687          $record = (array)$record;
 688  
 689          if (!isset($record['name'])) {
 690              $record['name'] = 'Test scale '.$i;
 691          }
 692  
 693          if (!isset($record['scale'])) {
 694              $record['scale'] = 'A,B,C,D,F';
 695          }
 696  
 697          if (!isset($record['courseid'])) {
 698              $record['courseid'] = 0;
 699          }
 700  
 701          if (!isset($record['userid'])) {
 702              $record['userid'] = 0;
 703          }
 704  
 705          if (!isset($record['description'])) {
 706              $record['description'] = 'Test scale description '.$i;
 707          }
 708  
 709          if (!isset($record['descriptionformat'])) {
 710              $record['descriptionformat'] = FORMAT_MOODLE;
 711          }
 712  
 713          $record['timemodified'] = time();
 714  
 715          if (isset($record['id'])) {
 716              $DB->import_record('scale', $record);
 717              $DB->get_manager()->reset_sequence('scale');
 718              $id = $record['id'];
 719          } else {
 720              $id = $DB->insert_record('scale', $record);
 721          }
 722  
 723          return $DB->get_record('scale', array('id'=>$id), '*', MUST_EXIST);
 724      }
 725  
 726      /**
 727       * Creates a new role in the system.
 728       *
 729       * You can fill $record with the role 'name',
 730       * 'shortname', 'description' and 'archetype'.
 731       *
 732       * If an archetype is specified it's capabilities,
 733       * context where the role can be assigned and
 734       * all other properties are copied from the archetype;
 735       * if no archetype is specified it will create an
 736       * empty role.
 737       *
 738       * @param array|stdClass $record
 739       * @return int The new role id
 740       */
 741      public function create_role($record=null) {
 742          global $DB;
 743  
 744          $this->rolecount++;
 745          $i = $this->rolecount;
 746  
 747          $record = (array)$record;
 748  
 749          if (empty($record['shortname'])) {
 750              $record['shortname'] = 'role-' . $i;
 751          }
 752  
 753          if (empty($record['name'])) {
 754              $record['name'] = 'Test role ' . $i;
 755          }
 756  
 757          if (empty($record['description'])) {
 758              $record['description'] = 'Test role ' . $i . ' description';
 759          }
 760  
 761          if (empty($record['archetype'])) {
 762              $record['archetype'] = '';
 763          } else {
 764              $archetypes = get_role_archetypes();
 765              if (empty($archetypes[$record['archetype']])) {
 766                  throw new coding_exception('\'role\' requires the field \'archetype\' to specify a ' .
 767                      'valid archetype shortname (editingteacher, student...)');
 768              }
 769          }
 770  
 771          // Creates the role.
 772          if (!$newroleid = create_role($record['name'], $record['shortname'], $record['description'], $record['archetype'])) {
 773              throw new coding_exception('There was an error creating \'' . $record['shortname'] . '\' role');
 774          }
 775  
 776          // If no archetype was specified we allow it to be added to all contexts,
 777          // otherwise we allow it in the archetype contexts.
 778          if (!$record['archetype']) {
 779              $contextlevels = array_keys(context_helper::get_all_levels());
 780          } else {
 781              // Copying from the archetype default rol.
 782              $archetyperoleid = $DB->get_field(
 783                  'role',
 784                  'id',
 785                  array('shortname' => $record['archetype'], 'archetype' => $record['archetype'])
 786              );
 787              $contextlevels = get_role_contextlevels($archetyperoleid);
 788          }
 789          set_role_contextlevels($newroleid, $contextlevels);
 790  
 791          if ($record['archetype']) {
 792  
 793              // We copy all the roles the archetype can assign, override and switch to.
 794              if ($record['archetype']) {
 795                  $types = array('assign', 'override', 'switch');
 796                  foreach ($types as $type) {
 797                      $rolestocopy = get_default_role_archetype_allows($type, $record['archetype']);
 798                      foreach ($rolestocopy as $tocopy) {
 799                          $functionname = 'allow_' . $type;
 800                          $functionname($newroleid, $tocopy);
 801                      }
 802                  }
 803              }
 804  
 805              // Copying the archetype capabilities.
 806              $sourcerole = $DB->get_record('role', array('id' => $archetyperoleid));
 807              role_cap_duplicate($sourcerole, $newroleid);
 808          }
 809  
 810          return $newroleid;
 811      }
 812  
 813      /**
 814       * Create a tag.
 815       *
 816       * @param array|stdClass $record
 817       * @return stdClass the tag record
 818       */
 819      public function create_tag($record = null) {
 820          global $DB, $USER;
 821  
 822          $this->tagcount++;
 823          $i = $this->tagcount;
 824  
 825          $record = (array) $record;
 826  
 827          if (!isset($record['userid'])) {
 828              $record['userid'] = $USER->id;
 829          }
 830  
 831          if (!isset($record['rawname'])) {
 832              if (isset($record['name'])) {
 833                  $record['rawname'] = $record['name'];
 834              } else {
 835                  $record['rawname'] = 'Tag name ' . $i;
 836              }
 837          }
 838  
 839          // Attribute 'name' should be a lowercase version of 'rawname', if not set.
 840          if (!isset($record['name'])) {
 841              $record['name'] = core_text::strtolower($record['rawname']);
 842          } else {
 843              $record['name'] = core_text::strtolower($record['name']);
 844          }
 845  
 846          if (!isset($record['tagcollid'])) {
 847              $record['tagcollid'] = core_tag_collection::get_default();
 848          }
 849  
 850          if (!isset($record['description'])) {
 851              $record['description'] = 'Tag description';
 852          }
 853  
 854          if (!isset($record['descriptionformat'])) {
 855              $record['descriptionformat'] = FORMAT_MOODLE;
 856          }
 857  
 858          if (!isset($record['flag'])) {
 859              $record['flag'] = 0;
 860          }
 861  
 862          if (!isset($record['timemodified'])) {
 863              $record['timemodified'] = time();
 864          }
 865  
 866          $id = $DB->insert_record('tag', $record);
 867  
 868          return $DB->get_record('tag', array('id' => $id), '*', MUST_EXIST);
 869      }
 870  
 871      /**
 872       * Helper method which combines $defaults with the values specified in $record.
 873       * If $record is an object, it is converted to an array.
 874       * Then, for each key that is in $defaults, but not in $record, the value
 875       * from $defaults is copied.
 876       * @param array $defaults the default value for each field with
 877       * @param array|stdClass $record
 878       * @return array updated $record.
 879       */
 880      public function combine_defaults_and_record(array $defaults, $record) {
 881          $record = (array) $record;
 882  
 883          foreach ($defaults as $key => $defaults) {
 884              if (!array_key_exists($key, $record)) {
 885                  $record[$key] = $defaults;
 886              }
 887          }
 888          return $record;
 889      }
 890  
 891      /**
 892       * Simplified enrolment of user to course using default options.
 893       *
 894       * It is strongly recommended to use only this method for 'manual' and 'self' plugins only!!!
 895       *
 896       * @param int $userid
 897       * @param int $courseid
 898       * @param int|string $roleidorshortname optional role id or role shortname, use only with manual plugin
 899       * @param string $enrol name of enrol plugin,
 900       *     there must be exactly one instance in course,
 901       *     it must support enrol_user() method.
 902       * @param int $timestart (optional) 0 means unknown
 903       * @param int $timeend (optional) 0 means forever
 904       * @param int $status (optional) default to ENROL_USER_ACTIVE for new enrolments
 905       * @return bool success
 906       */
 907      public function enrol_user($userid, $courseid, $roleidorshortname = null, $enrol = 'manual',
 908              $timestart = 0, $timeend = 0, $status = null) {
 909          global $DB;
 910  
 911          // If role is specified by shortname, convert it into an id.
 912          if (!is_numeric($roleidorshortname) && is_string($roleidorshortname)) {
 913              $roleid = $DB->get_field('role', 'id', array('shortname' => $roleidorshortname), MUST_EXIST);
 914          } else {
 915              $roleid = $roleidorshortname;
 916          }
 917  
 918          if (!$plugin = enrol_get_plugin($enrol)) {
 919              return false;
 920          }
 921  
 922          $instances = $DB->get_records('enrol', array('courseid'=>$courseid, 'enrol'=>$enrol));
 923          if (count($instances) != 1) {
 924              return false;
 925          }
 926          $instance = reset($instances);
 927  
 928          if (is_null($roleid) and $instance->roleid) {
 929              $roleid = $instance->roleid;
 930          }
 931  
 932          $plugin->enrol_user($instance, $userid, $roleid, $timestart, $timeend, $status);
 933          return true;
 934      }
 935  
 936      /**
 937       * Assigns the specified role to a user in the context.
 938       *
 939       * @param int $roleid
 940       * @param int $userid
 941       * @param int $contextid Defaults to the system context
 942       * @return int new/existing id of the assignment
 943       */
 944      public function role_assign($roleid, $userid, $contextid = false) {
 945  
 946          // Default to the system context.
 947          if (!$contextid) {
 948              $context = context_system::instance();
 949              $contextid = $context->id;
 950          }
 951  
 952          if (empty($roleid)) {
 953              throw new coding_exception('roleid must be present in testing_data_generator::role_assign() arguments');
 954          }
 955  
 956          if (empty($userid)) {
 957              throw new coding_exception('userid must be present in testing_data_generator::role_assign() arguments');
 958          }
 959  
 960          return role_assign($roleid, $userid, $contextid);
 961      }
 962  
 963      /**
 964       * Create a grade_category.
 965       *
 966       * @param array|stdClass $record
 967       * @return stdClass the grade category record
 968       */
 969      public function create_grade_category($record = null) {
 970          global $CFG;
 971  
 972          $this->gradecategorycounter++;
 973  
 974          $record = (array)$record;
 975  
 976          if (empty($record['courseid'])) {
 977              throw new coding_exception('courseid must be present in testing::create_grade_category() $record');
 978          }
 979  
 980          if (!isset($record['fullname'])) {
 981              $record['fullname'] = 'Grade category ' . $this->gradecategorycounter;
 982          }
 983  
 984          // For gradelib classes.
 985          require_once($CFG->libdir . '/gradelib.php');
 986          // Create new grading category in this course.
 987          $gradecategory = new grade_category(array('courseid' => $record['courseid']), false);
 988          $gradecategory->apply_default_settings();
 989          grade_category::set_properties($gradecategory, $record);
 990          $gradecategory->apply_forced_settings();
 991          $gradecategory->insert();
 992  
 993          // This creates a default grade item for the category
 994          $gradeitem = $gradecategory->load_grade_item();
 995  
 996          $gradecategory->update_from_db();
 997          return $gradecategory->get_record_data();
 998      }
 999  
1000      /**
1001       * Create a grade_item.
1002       *
1003       * @param array|stdClass $record
1004       * @return stdClass the grade item record
1005       */
1006      public function create_grade_item($record = null) {
1007          global $CFG;
1008          require_once("$CFG->libdir/gradelib.php");
1009  
1010          $this->gradeitemcounter++;
1011  
1012          if (!isset($record['itemtype'])) {
1013              $record['itemtype'] = 'manual';
1014          }
1015  
1016          if (!isset($record['itemname'])) {
1017              $record['itemname'] = 'Grade item ' . $this->gradeitemcounter;
1018          }
1019  
1020          if (isset($record['outcomeid'])) {
1021              $outcome = new grade_outcome(array('id' => $record['outcomeid']));
1022              $record['scaleid'] = $outcome->scaleid;
1023          }
1024          if (isset($record['scaleid'])) {
1025              $record['gradetype'] = GRADE_TYPE_SCALE;
1026          } else if (!isset($record['gradetype'])) {
1027              $record['gradetype'] = GRADE_TYPE_VALUE;
1028          }
1029  
1030          // Create new grade item in this course.
1031          $gradeitem = new grade_item($record, false);
1032          $gradeitem->insert();
1033  
1034          $gradeitem->update_from_db();
1035          return $gradeitem->get_record_data();
1036      }
1037  
1038      /**
1039       * Create a grade_outcome.
1040       *
1041       * @param array|stdClass $record
1042       * @return stdClass the grade outcome record
1043       */
1044      public function create_grade_outcome($record = null) {
1045          global $CFG;
1046  
1047          $this->gradeoutcomecounter++;
1048          $i = $this->gradeoutcomecounter;
1049  
1050          if (!isset($record['fullname'])) {
1051              $record['fullname'] = 'Grade outcome ' . $i;
1052          }
1053  
1054          // For gradelib classes.
1055          require_once($CFG->libdir . '/gradelib.php');
1056          // Create new grading outcome in this course.
1057          $gradeoutcome = new grade_outcome($record, false);
1058          $gradeoutcome->insert();
1059  
1060          $gradeoutcome->update_from_db();
1061          return $gradeoutcome->get_record_data();
1062      }
1063  }


Generated: Thu Aug 11 10:00:09 2016 Cross-referenced by PHPXref 0.7.1