Search moodle.org's
Developer Documentation

See Release Notes
Long Term Support Release

  • Bug fixes for general core bugs in 4.1.x will end 13 November 2023 (12 months).
  • Bug fixes for security issues in 4.1.x will end 10 November 2025 (36 months).
  • PHP version: minimum PHP 7.4.0 Note: minimum PHP version has increased since Moodle 4.0. PHP 8.0.x is supported too.

Differences Between: [Versions 310 and 401] [Versions 39 and 401]

   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   * This file contains helper classes and functions for testing.
  19   *
  20   * @package core_calendar
  21   * @copyright 2017 Ryan Wyllie <ryan@moodle.com>
  22   * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
  23   */
  24  
  25  defined('MOODLE_INTERNAL') || die();
  26  
  27  global $CFG;
  28  
  29  require_once($CFG->dirroot . '/calendar/lib.php');
  30  
  31  use core_calendar\local\event\entities\action_event;
  32  use core_calendar\local\event\entities\event;
  33  use core_calendar\local\event\entities\repeat_event_collection;
  34  use core_calendar\local\event\proxies\std_proxy;
  35  use core_calendar\local\event\proxies\coursecat_proxy;
  36  use core_calendar\local\event\proxies\cm_info_proxy;
  37  use core_calendar\local\event\value_objects\action;
  38  use core_calendar\local\event\value_objects\event_description;
  39  use core_calendar\local\event\value_objects\event_times;
  40  use core_calendar\local\event\factories\event_factory_interface;
  41  
  42  /**
  43   * Create a calendar event with the given properties.
  44   *
  45   * @param array $properties The properties to set on the event
  46   * @return \calendar_event
  47   */
  48  function create_event($properties) {
  49      $record = new \stdClass();
  50      $record->name = 'event name';
  51      $record->eventtype = 'site';
  52      $record->repeat = 0;
  53      $record->repeats = 0;
  54      $record->timestart = time();
  55      $record->timeduration = 0;
  56      $record->timesort = 0;
  57      $record->type = CALENDAR_EVENT_TYPE_STANDARD;
  58      $record->courseid = 0;
  59      $record->categoryid = 0;
  60  
  61      foreach ($properties as $name => $value) {
  62          $record->$name = $value;
  63      }
  64  
  65      $event = new \calendar_event($record);
  66      return $event->create($record);
  67  }
  68  
  69  /**
  70   * Helper function to create a x number of events for each event type.
  71   *
  72   * @param int $quantity The quantity of events to be created.
  73   * @return array List of created events.
  74   */
  75  function create_standard_events(int $quantity): array {
  76      $types = ['site', 'category', 'course', 'group', 'user'];
  77  
  78      $events = [];
  79      foreach ($types as $eventtype) {
  80          // Create five events of each event type.
  81          for ($i = 0; $i < $quantity; $i++) {
  82              $events[] = create_event(['eventtype' => $eventtype]);
  83          }
  84      }
  85  
  86      return $events;
  87  }
  88  
  89  /**
  90   * Helper function to create an action event.
  91   *
  92   * @param array $data The event data.
  93   * @return bool|calendar_event
  94   */
  95  function create_action_event(array $data) {
  96      global $CFG;
  97  
  98      require_once($CFG->dirroot . '/calendar/lib.php');
  99  
 100      if (!isset($data['modulename']) || !isset($data['instance'])) {
 101          throw new coding_exception('Module and instance should be specified when creating an action event.');
 102      }
 103  
 104      $isuseroverride = isset($data->priority) && $data->priority == CALENDAR_EVENT_USER_OVERRIDE_PRIORITY;
 105      if ($isuseroverride) {
 106          if (!in_array($data['modulename'], ['assign', 'lesson', 'quiz'])) {
 107              throw new coding_exception('Only assign, lesson and quiz modules supports overrides');
 108          }
 109      }
 110  
 111      $event = array_merge($data, [
 112          'eventtype' => isset($data['eventtype']) ? $data['eventtype'] : 'open',
 113          'courseid' => isset($data['courseid']) ? $data['courseid'] : 0,
 114          'instance' => $data['instance'],
 115          'modulename' => $data['modulename'],
 116          'type' => CALENDAR_EVENT_TYPE_ACTION,
 117      ]);
 118  
 119      return create_event($event);
 120  }
 121  
 122  /**
 123   * Helper function to create an user override calendar event.
 124   *
 125   * @param string $modulename The modulename.
 126   * @param int $instanceid The instance id.
 127   * @param int $userid The user id.
 128   * @return calendar_event|false
 129   */
 130  function create_user_override_event(string $modulename, int $instanceid, int $userid) {
 131      if (!isset($userid)) {
 132          throw new coding_exception('Must specify userid when creating a user override.');
 133      }
 134  
 135      return create_action_event([
 136          'modulename' => $modulename,
 137          'instance' => $instanceid,
 138          'userid' => $userid,
 139          'priority' => CALENDAR_EVENT_USER_OVERRIDE_PRIORITY,
 140      ]);
 141  }
 142  
 143  /**
 144   * Helper function to create an group override calendar event.
 145   *
 146   * @param string $modulename The modulename.
 147   * @param int $instanceid The instance id.
 148   * @param int $courseid The course id.
 149   * @param int $groupid The group id.
 150   * @return calendar_event|false
 151   */
 152  function create_group_override_event(string $modulename, int $instanceid, int $courseid, int $groupid) {
 153      if (!isset($groupid)) {
 154          throw new coding_exception('Must specify groupid when creating a group override.');
 155      }
 156  
 157      return create_action_event([
 158          'groupid' => $groupid,
 159          'courseid' => $courseid,
 160          'modulename' => $modulename,
 161          'instance' => $instanceid,
 162      ]);
 163  }
 164  
 165  /**
 166   * A test factory that will create action events.
 167   *
 168   * @copyright 2017 Ryan Wyllie <ryan@moodle.com>
 169   * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or late
 170   */
 171  class action_event_test_factory implements event_factory_interface {
 172  
 173      /**
 174       * @var callable $callback.
 175       */
 176      private $callback;
 177  
 178      /**
 179       * A test factory that will create action events. The factory accepts a callback
 180       * that will be used to determine if the event should be returned or not.
 181       *
 182       * The callback will be given the event and should return true if the event
 183       * should be returned and false otherwise.
 184       *
 185       * @param callable $callback The callback.
 186       */
 187      public function __construct($callback = null) {
 188          $this->callback = $callback;
 189      }
 190  
 191      public function create_instance(\stdClass $record) {
 192          $module = null;
 193          $subscription = null;
 194  
 195          if ($record->instance && $record->modulename) {
 196              $module = new cm_info_proxy($record->instance, $record->modulename, $record->courseid);
 197          }
 198  
 199          if ($record->subscriptionid) {
 200              $subscription = new std_proxy($record->subscriptionid, function($id) {
 201                  return (object)['id' => $id];
 202              });
 203          }
 204  
 205          $event = new event(
 206              $record->id,
 207              $record->name,
 208              new event_description($record->description, $record->format),
 209              new coursecat_proxy($record->categoryid),
 210              new std_proxy($record->courseid, function($id) {
 211                  $course = new \stdClass();
 212                  $course->id = $id;
 213                  return $course;
 214              }),
 215              new std_proxy($record->groupid, function($id) {
 216                  $group = new \stdClass();
 217                  $group->id = $id;
 218                  return $group;
 219              }),
 220              new std_proxy($record->userid, function($id) {
 221                  $user = new \stdClass();
 222                  $user->id = $id;
 223                  return $user;
 224              }),
 225              !empty($record->repeatid) ? new repeat_event_collection($record, $this) : null,
 226              $module,
 227              $record->eventtype,
 228              new event_times(
 229                  (new \DateTimeImmutable())->setTimestamp($record->timestart),
 230                  (new \DateTimeImmutable())->setTimestamp($record->timestart + $record->timeduration),
 231                  (new \DateTimeImmutable())->setTimestamp($record->timesort ? $record->timesort : $record->timestart),
 232                  (new \DateTimeImmutable())->setTimestamp($record->timemodified),
 233                  (new \DateTimeImmutable())->setTimestamp($record->timesort ? usergetmidnight($record->timesort) : 0)
 234              ),
 235              !empty($record->visible),
 236              $subscription,
 237              $record->location,
 238              !empty($record->component) ? $record->component : null
 239          );
 240  
 241          $action = new action(
 242              'Test action',
 243              new \moodle_url('/'),
 244              1,
 245              true
 246          );
 247  
 248          $actionevent = new action_event($event, $action);
 249  
 250          if ($callback = $this->callback) {
 251              return $callback($actionevent) ? $actionevent : false;
 252          } else {
 253              return $actionevent;
 254          }
 255      }
 256  }