MDL-57503 calendar: external function get action events by course
[moodle.git] / calendar / classes / external / events_related_objects_cache.php
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/>.
17 /**
18  * Contains event class for providing the related objects when exporting
19  * a list of calendar events.
20  *
21  * @package   core_calendar
22  * @copyright 2017 Ryan Wyllie <ryan@moodle.com>
23  * @license   http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
24  */
26 namespace core_calendar\external;
28 defined('MOODLE_INTERNAL') || die();
30 use \core_calendar\local\interfaces\event_interface;
32 /**
33  * Class to providing the related objects when exporting
34  * a list of calendar events.
35  *
36  * This class is only meant for use with exporters. It attempts to bulk load
37  * the related objects for a list of events and cache them to avoid having
38  * to query the database when exporting each individual event.
39  *
40  * @package   core_calendar
41  * @copyright 2017 Ryan Wyllie <ryan@moodle.com>
42  * @license   http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
43  */
44 class events_related_objects_cache {
46     /**
47      * @var array $events The events for which we need related objects.
48      */
49     protected $events;
51     /**
52      * @var array $courses The related courses.
53      */
54     protected $courses = null;
56     /**
57      * @var array $events The related groups.
58      */
59     protected $groups = null;
61     /**
62      * @var array $events The related course modules.
63      */
64     protected $coursemodules = [];
66     /**
67      * Constructor.
68      *
69      * @param array $event Array of event_interface events
70      * @param array $courses Array of courses to populate the cache with
71      */
72     public function __construct(array $events, array $courses = null) {
73         $this->events = $events;
75         if (!is_null($courses)) {
76             $this->courses = [];
78             foreach ($courses as $course) {
79                 $this->courses[$course->id] = $course;
80             }
81         }
82     }
84     /**
85      * Get the related course object for a given event.
86      *
87      * @param event_interface $event.
88      * @return stdClass|null
89      */
90     public function get_course(event_interface $event) {
91         if (is_null($this->courses)) {
92             $this->load_courses();
93         }
95         if ($course = $event->get_course()) {
96             $courseid = $course->get('id');
97             return isset($this->courses[$courseid]) ? $this->courses[$courseid] : null;
98         } else {
99             return null;
100         }
101     }
103     /**
104      * Get the related context for a given event.
105      *
106      * @param event_interface $event.
107      * @return context|null
108      */
109     public function get_context(event_interface $event) {
110         global $USER;
112         $courseid = $event->get_course() ? $event->get_course()->get('id') : null;
113         $groupid = $event->get_group() ? $event->get_group()->get('id') : null;
114         $userid = $event->get_user() ? $event->get_user()->get('id') : null;
115         $moduleid = $event->get_course_module() ? $event->get_course_module()->get('id') : null;
117         if (!empty($courseid)) {
118             return \context_course::instance($event->get_course()->get('id'));
119         } else if (!empty($groupid)) {
120             $group = $this->get_group($event);
121             return \context_course::instance($group->courseid);
122         } else if (!empty($userid) && $userid == $USER->id) {
123             return \context_user::instance($userid);
124         } else if (!empty($userid) && $userid != $USER->id && $moduleid && $moduleid > 0) {
125             $cm = $this->get_course_module($event);
126             return \context_course::instance($cm->course);
127         } else {
128             return \context_user::instance($userid);
129         }
130     }
132     /**
133      * Get the related group object for a given event.
134      *
135      * @param event_interface $event.
136      * @return stdClass|null
137      */
138     public function get_group(event_interface $event) {
139         if (is_null($this->groups)) {
140             $this->load_groups();
141         }
143         if ($group = $event->get_group()) {
144             $groupid = $group->get('id');
145             return isset($this->groups[$groupid]) ? $this->groups[$groupid] : null;
146         } else {
147             return null;
148         }
149     }
151     /**
152      * Get the related course module for a given event.
153      *
154      * @param event_interface $event.
155      * @return stdClass|null
156      */
157     public function get_course_module(event_interface $event) {
158         if (!$event->get_course_module()) {
159             return null;
160         }
162         $id = $event->get_course_module()->get('id');
163         $name = $event->get_course_module()->get('modname');
164         $key = $name . '_' . $id;
166         if (!isset($this->coursemodules[$key])) {
167             $this->coursemodules[$key] = get_coursemodule_from_instance($name, $id, 0, false, MUST_EXIST);
168         }
170         return $this->coursemodules[$key];
171     }
173     /**
174      * Load the list of all of the distinct courses required for the
175      * list of provided events and save the result in memory.
176      */
177     protected function load_courses() {
178         global $DB;
180         $courseids = [];
181         foreach ($this->events as $event) {
182             if ($course = $event->get_course()) {
183                 $id = $course->get('id');
184                 $courseids[$id] = true;
185             }
186         }
188         if (empty($courseids)) {
189             $this->courses = [];
190             return;
191         }
193         list($idsql, $params) = $DB->get_in_or_equal(array_keys($courseids));
194         $sql = "SELECT * FROM {course} WHERE id {$idsql}";
196         $this->courses = $DB->get_records_sql($sql, $params);
197     }
199     /**
200      * Load the list of all of the distinct groups required for the
201      * list of provided events and save the result in memory.
202      */
203     protected function load_groups() {
204         global $DB;
206         $groupids = [];
207         foreach ($this->events as $event) {
208             if ($group = $event->get_group()) {
209                 $id = $group->get('id');
210                 $groupids[$id] = true;
211             }
212         }
214         if (empty($groupids)) {
215             $this->groups = [];
216             return;
217         }
219         list($idsql, $params) = $DB->get_in_or_equal(array_keys($groupids));
220         $sql = "SELECT * FROM {groups} WHERE id {$idsql}";
222         $this->groups = $DB->get_records_sql($sql, $params);
223     }