MDL-59366 enrol: Add $onlyenabled param in enrol instances getters
[moodle.git] / user / index.php
CommitLineData
aa6c1ced 1<?php
a2ed6e69
SH
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 * Lists all the users within a given course.
19 *
20 * @copyright 1999 Martin Dougiamas http://dougiamas.com
21 * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
22 * @package core_user
23 */
24
25require_once('../config.php');
0ff203b6 26require_once($CFG->dirroot.'/user/lib.php');
a2ed6e69
SH
27require_once($CFG->libdir.'/tablelib.php');
28require_once($CFG->libdir.'/filelib.php');
a78ed71c 29require_once($CFG->dirroot.'/enrol/locallib.php');
a2ed6e69 30
a2ed6e69
SH
31define('DEFAULT_PAGE_SIZE', 20);
32define('SHOW_ALL_PAGE_SIZE', 5000);
a2ed6e69
SH
33
34$page = optional_param('page', 0, PARAM_INT); // Which page to show.
35$perpage = optional_param('perpage', DEFAULT_PAGE_SIZE, PARAM_INT); // How many per page.
a2ed6e69
SH
36$accesssince = optional_param('accesssince', 0, PARAM_INT); // Filter by last access. -1 = never.
37$search = optional_param('search', '', PARAM_RAW); // Make sure it is processed with p() or s() when sending to output!
38$roleid = optional_param('roleid', 0, PARAM_INT); // Optional roleid, 0 means all enrolled users (or all on the frontpage).
39$contextid = optional_param('contextid', 0, PARAM_INT); // One of this or.
40$courseid = optional_param('id', 0, PARAM_INT); // This are required.
5b7c500a 41$selectall = optional_param('selectall', false, PARAM_BOOL); // When rendering checkboxes against users mark them all checked.
a2ed6e69
SH
42
43$PAGE->set_url('/user/index.php', array(
44 'page' => $page,
45 'perpage' => $perpage,
a2ed6e69
SH
46 'accesssince' => $accesssince,
47 'search' => $search,
48 'roleid' => $roleid,
49 'contextid' => $contextid,
50 'id' => $courseid));
51
52if ($contextid) {
53 $context = context::instance_by_id($contextid, MUST_EXIST);
54 if ($context->contextlevel != CONTEXT_COURSE) {
55 print_error('invalidcontext');
56 }
57 $course = $DB->get_record('course', array('id' => $context->instanceid), '*', MUST_EXIST);
58} else {
59 $course = $DB->get_record('course', array('id' => $courseid), '*', MUST_EXIST);
60 $context = context_course::instance($course->id, MUST_EXIST);
61}
62// Not needed anymore.
63unset($contextid);
64unset($courseid);
f9903ed0 65
a2ed6e69 66require_login($course);
f9903ed0 67
a2ed6e69
SH
68$systemcontext = context_system::instance();
69$isfrontpage = ($course->id == SITEID);
f9903ed0 70
a2ed6e69 71$frontpagectx = context_course::instance(SITEID);
4f0c2d00 72
a2ed6e69
SH
73if ($isfrontpage) {
74 $PAGE->set_pagelayout('admin');
75 require_capability('moodle/site:viewparticipants', $systemcontext);
76} else {
77 $PAGE->set_pagelayout('incourse');
78 require_capability('moodle/course:viewparticipants', $context);
79}
224aa44a 80
a2ed6e69 81$rolenamesurl = new moodle_url("$CFG->wwwroot/user/index.php?contextid=$context->id&sifirst=&silast=");
6d3c57f4 82
a2ed6e69
SH
83$rolenames = role_fix_names(get_profile_roles($context), $context, ROLENAME_ALIAS, true);
84if ($isfrontpage) {
85 $rolenames[0] = get_string('allsiteusers', 'role');
86} else {
87 $rolenames[0] = get_string('allparticipants');
88}
d7270311 89
a2ed6e69
SH
90// Make sure other roles may not be selected by any means.
91if (empty($rolenames[$roleid])) {
92 print_error('noparticipants');
93}
5f9e296a 94
a2ed6e69
SH
95// No roles to display yet?
96// frontpage course is an exception, on the front page course we should display all users.
97if (empty($rolenames) && !$isfrontpage) {
98 if (has_capability('moodle/role:assign', $context)) {
99 redirect($CFG->wwwroot.'/'.$CFG->admin.'/roles/assign.php?contextid='.$context->id);
100 } else {
4f0c2d00 101 print_error('noparticipants');
5f9e296a 102 }
a2ed6e69 103}
5f9e296a 104
0ff203b6
JL
105// Trigger events.
106user_list_view($course, $context);
a2ed6e69
SH
107
108$bulkoperations = has_capability('moodle/course:bulkmessaging', $context);
109
110$countries = get_string_manager()->get_list_of_countries();
111
a78ed71c
DW
112// Manage enrolments.
113$manager = new course_enrolment_manager($PAGE, $course);
114$enrolbuttons = $manager->get_manual_enrol_buttons();
115
a2ed6e69
SH
116// Check to see if groups are being used in this course
117// and if so, set $currentgroup to reflect the current group.
ff3caf30 118
a2ed6e69
SH
119$groupmode = groups_get_course_groupmode($course); // Groups are being used.
120$currentgroup = groups_get_course_group($course, true);
ff3caf30 121
a2ed6e69
SH
122if (!$currentgroup) { // To make some other functions work better later.
123 $currentgroup = null;
124}
ff3caf30 125
a2ed6e69 126$isseparategroups = ($course->groupmode == SEPARATEGROUPS and !has_capability('moodle/site:accessallgroups', $context));
ff3caf30 127
a2ed6e69
SH
128$PAGE->set_title("$course->shortname: ".get_string('participants'));
129$PAGE->set_heading($course->fullname);
130$PAGE->set_pagetype('course-view-' . $course->format);
131$PAGE->add_body_class('path-user'); // So we can style it independently.
132$PAGE->set_other_editing_capability('moodle/course:manageactivities');
2cb2ce61 133
a2ed6e69 134echo $OUTPUT->header();
4e1f6047 135echo $OUTPUT->heading(get_string('participants'));
caa8363f 136
a78ed71c
DW
137$enrolrenderer = $PAGE->get_renderer('core_enrol');
138echo '<div class="pull-right">';
139foreach ($enrolbuttons as $enrolbutton) {
140 echo $enrolrenderer->render($enrolbutton);
141}
142echo '</div>';
143
a2ed6e69 144echo '<div class="userlist">';
0be6f678 145
a2ed6e69
SH
146if ($isseparategroups and (!$currentgroup) ) {
147 // The user is not in the group so show message and exit.
148 echo $OUTPUT->heading(get_string("notingroup"));
149 echo $OUTPUT->footer();
150 exit;
151}
99cca847 152
a2ed6e69
SH
153// Should use this variable so that we don't break stuff every time a variable is added or changed.
154$baseurl = new moodle_url('/user/index.php', array(
155 'contextid' => $context->id,
156 'roleid' => $roleid,
157 'id' => $course->id,
158 'perpage' => $perpage,
159 'accesssince' => $accesssince,
160 'search' => s($search)));
161
162// Setting up tags.
163if ($course->id == SITEID) {
164 $filtertype = 'site';
165} else if ($course->id && !$currentgroup) {
166 $filtertype = 'course';
167 $filterselect = $course->id;
168} else {
169 $filtertype = 'group';
170 $filterselect = $currentgroup;
171}
03d9401e 172
a2ed6e69
SH
173// Print settings and things in a table across the top.
174$controlstable = new html_table();
175$controlstable->attributes['class'] = 'controls';
176$controlstable->cellspacing = 0;
177$controlstable->data[] = new html_table_row();
178
24c3db91
DP
179if ($groupmenu = groups_print_course_menu($course, $baseurl->out(), true)) {
180 $controlstable->data[0]->cells[] = $groupmenu;
181}
a2ed6e69 182
bc47b706
MN
183// Get the list of fields we have to hide.
184$hiddenfields = array();
185if (!has_capability('moodle/course:viewhiddenuserfields', $context)) {
186 $hiddenfields = array_flip(explode(',', $CFG->hiddenuserfields));
187}
188
189// If lastaccess is in the hidden fields access do not allow filtering.
190if (isset($hiddenfields['lastaccess'])) {
191 $accesssince = 0;
192} else { // The user is allowed to filter by last access.
a2ed6e69
SH
193 // Get minimum lastaccess for this course and display a dropbox to filter by lastaccess going back this far.
194 // We need to make it diferently for normal courses and site course.
195 if (!$isfrontpage) {
196 $minlastaccess = $DB->get_field_sql('SELECT min(timeaccess)
197 FROM {user_lastaccess}
198 WHERE courseid = ?
199 AND timeaccess != 0', array($course->id));
200 $lastaccess0exists = $DB->record_exists('user_lastaccess', array('courseid' => $course->id, 'timeaccess' => 0));
201 } else {
202 $minlastaccess = $DB->get_field_sql('SELECT min(lastaccess)
203 FROM {user}
204 WHERE lastaccess != 0');
205 $lastaccess0exists = $DB->record_exists('user', array('lastaccess' => 0));
7da0af9f 206 }
87a13824 207
a2ed6e69
SH
208 $now = usergetmidnight(time());
209 $timeaccess = array();
210 $baseurl->remove_params('accesssince');
87a13824 211
a2ed6e69
SH
212 // Makes sense for this to go first.
213 $timeoptions[0] = get_string('selectperiod');
87a13824 214
a2ed6e69
SH
215 // Days.
216 for ($i = 1; $i < 7; $i++) {
217 if (strtotime('-'.$i.' days', $now) >= $minlastaccess) {
218 $timeoptions[strtotime('-'.$i.' days', $now)] = get_string('numdays', 'moodle', $i);
ca792680 219 }
a2ed6e69
SH
220 }
221 // Weeks.
222 for ($i = 1; $i < 10; $i++) {
223 if (strtotime('-'.$i.' weeks', $now) >= $minlastaccess) {
224 $timeoptions[strtotime('-'.$i.' weeks', $now)] = get_string('numweeks', 'moodle', $i);
5ff311f0 225 }
a2ed6e69
SH
226 }
227 // Months.
228 for ($i = 2; $i < 12; $i++) {
229 if (strtotime('-'.$i.' months', $now) >= $minlastaccess) {
230 $timeoptions[strtotime('-'.$i.' months', $now)] = get_string('nummonths', 'moodle', $i);
31b71336 231 }
a2ed6e69
SH
232 }
233 // Try a year.
234 if (strtotime('-1 year', $now) >= $minlastaccess) {
235 $timeoptions[strtotime('-1 year', $now)] = get_string('lastyear');
236 }
87a13824 237
a2ed6e69
SH
238 if (!empty($lastaccess0exists)) {
239 $timeoptions[-1] = get_string('never');
240 }
87a13824 241
a2ed6e69
SH
242 if (count($timeoptions) > 1) {
243 $select = new single_select($baseurl, 'accesssince', $timeoptions, $accesssince, null, 'timeoptions');
244 $select->set_label(get_string('usersnoaccesssince'));
245 $controlstable->data[0]->cells[] = $OUTPUT->render($select);
77c645df 246 }
a2ed6e69 247}
87a13824 248
a2ed6e69
SH
249echo html_writer::table($controlstable);
250
bc47b706
MN
251$participanttable = new \core_user\participants_table($course->id, $currentgroup, $accesssince, $roleid, $search,
252 $bulkoperations, $selectall);
253$participanttable->define_baseurl($baseurl);
77c645df 254
bc47b706
MN
255// Do this so we can get the total number of rows.
256ob_start();
257$participanttable->out($perpage, true);
258$participanttablehtml = ob_get_contents();
259ob_end_clean();
3e219038 260
a2ed6e69
SH
261// If there are multiple Roles in the course, then show a drop down menu for switching.
262if (count($rolenames) > 1) {
263 echo '<div class="rolesform">';
32bd11cb
BB
264 echo $OUTPUT->single_select($rolenamesurl, 'roleid', $rolenames, $roleid, null,
265 'rolesform', array('label' => get_string('currentrole', 'role')));
a2ed6e69 266 echo '</div>';
5f9e296a 267
a2ed6e69
SH
268} else if (count($rolenames) == 1) {
269 // When all users with the same role - print its name.
270 echo '<div class="rolesform">';
271 echo get_string('role').get_string('labelsep', 'langconfig');
272 $rolename = reset($rolenames);
273 echo $rolename;
274 echo '</div>';
275}
3e219038 276
a2ed6e69
SH
277if ($roleid > 0) {
278 $a = new stdClass();
bc47b706 279 $a->number = $participanttable->totalrows;
a2ed6e69
SH
280 $a->role = $rolenames[$roleid];
281 $heading = format_string(get_string('xuserswiththerole', 'role', $a));
f642a21a 282
e727e91c
MN
283 if ($currentgroup) {
284 if ($group = groups_get_group($currentgroup)) {
285 $a->group = $group->name;
286 $heading .= ' ' . format_string(get_string('ingroup', 'role', $a));
287 }
a2ed6e69 288 }
f642a21a 289
9488b6f3 290 if ($accesssince && !empty($timeoptions[$accesssince])) {
a2ed6e69
SH
291 $a->timeperiod = $timeoptions[$accesssince];
292 $heading .= ' ' . format_string(get_string('inactiveformorethan', 'role', $a));
293 }
f642a21a 294
a2ed6e69 295 $heading .= ": $a->number";
b85b25eb 296
a2ed6e69
SH
297 echo $OUTPUT->heading($heading, 3);
298} else {
a2ed6e69
SH
299 if ($course->id == SITEID and $roleid < 0) {
300 $strallparticipants = get_string('allsiteusers', 'role');
301 } else {
302 $strallparticipants = get_string('allparticipants');
303 }
7057c3ef 304
bc47b706 305 echo $OUTPUT->heading($strallparticipants.get_string('labelsep', 'langconfig') . $participanttable->totalrows, 3);
a2ed6e69 306}
3e219038 307
a2ed6e69
SH
308if ($bulkoperations) {
309 echo '<form action="action_redir.php" method="post" id="participantsform">';
310 echo '<div>';
311 echo '<input type="hidden" name="sesskey" value="'.sesskey().'" />';
312 echo '<input type="hidden" name="returnto" value="'.s($PAGE->url->out(false)).'" />';
313}
77c645df 314
bc47b706 315echo $participanttablehtml;
4c7593ff 316
8dd42b38
AH
317$perpageurl = clone($baseurl);
318$perpageurl->remove_params('perpage');
bc47b706 319if ($perpage == SHOW_ALL_PAGE_SIZE && $participanttable->totalrows > DEFAULT_PAGE_SIZE) {
8dd42b38
AH
320 $perpageurl->param('perpage', DEFAULT_PAGE_SIZE);
321 echo $OUTPUT->container(html_writer::link($perpageurl, get_string('showperpage', '', DEFAULT_PAGE_SIZE)), array(), 'showall');
322
bc47b706 323} else if ($participanttable->get_page_size() < $participanttable->totalrows) {
8dd42b38 324 $perpageurl->param('perpage', SHOW_ALL_PAGE_SIZE);
bc47b706
MN
325 echo $OUTPUT->container(html_writer::link($perpageurl, get_string('showall', '', $participanttable->totalrows)),
326 array(), 'showall');
8dd42b38
AH
327}
328
a2ed6e69
SH
329if ($bulkoperations) {
330 echo '<br /><div class="buttons">';
5b7c500a 331
bc47b706 332 if ($participanttable->get_page_size() < $participanttable->totalrows) {
5b7c500a
AH
333 $perpageurl = clone($baseurl);
334 $perpageurl->remove_params('perpage');
335 $perpageurl->param('perpage', SHOW_ALL_PAGE_SIZE);
336 $perpageurl->param('selectall', true);
337 $showalllink = $perpageurl;
338 } else {
339 $showalllink = false;
340 }
341
b27c8d81 342 echo html_writer::start_tag('div', array('class' => 'btn-group'));
bc47b706 343 if ($participanttable->get_page_size() < $participanttable->totalrows) {
5b7c500a 344 // Select all users, refresh page showing all users and mark them all selected.
bc47b706 345 $label = get_string('selectalluserswithcount', 'moodle', $participanttable->totalrows);
b27c8d81
SB
346 echo html_writer::tag('input', "", array('type' => 'button', 'id' => 'checkall', 'class' => 'btn btn-secondary',
347 'value' => $label, 'data-showallink' => $showalllink));
5b7c500a 348 // Select all users, mark all users on page as selected.
b27c8d81
SB
349 echo html_writer::tag('input', "", array('type' => 'button', 'id' => 'checkallonpage', 'class' => 'btn btn-secondary',
350 'value' => get_string('selectallusersonpage')));
5b7c500a 351 } else {
b27c8d81
SB
352 echo html_writer::tag('input', "", array('type' => 'button', 'id' => 'checkallonpage', 'class' => 'btn btn-secondary',
353 'value' => get_string('selectall')));
5b7c500a
AH
354 }
355
b27c8d81
SB
356 echo html_writer::tag('input', "", array('type' => 'button', 'id' => 'checknone', 'class' => 'btn btn-secondary',
357 'value' => get_string('deselectall')));
358 echo html_writer::end_tag('div');
a2ed6e69
SH
359 $displaylist = array();
360 $displaylist['messageselect.php'] = get_string('messageselectadd');
361 if (!empty($CFG->enablenotes) && has_capability('moodle/notes:manage', $context) && $context->id != $frontpagectx->id) {
362 $displaylist['addnote.php'] = get_string('addnewnote', 'notes');
363 $displaylist['groupaddnote.php'] = get_string('groupaddnewnote', 'notes');
364 }
365
366 echo $OUTPUT->help_icon('withselectedusers');
367 echo html_writer::tag('label', get_string("withselectedusers"), array('for' => 'formactionid'));
368 echo html_writer::select($displaylist, 'formaction', '', array('' => 'choosedots'), array('id' => 'formactionid'));
369
370 echo '<input type="hidden" name="id" value="'.$course->id.'" />';
371 echo '<noscript style="display:inline">';
372 echo '<div><input type="submit" value="'.get_string('ok').'" /></div>';
373 echo '</noscript>';
374 echo '</div></div>';
375 echo '</form>';
376
377 $module = array('name' => 'core_user', 'fullpath' => '/user/module.js');
378 $PAGE->requires->js_init_call('M.core_user.init_participation', null, false, $module);
379}
b90e2f19 380
a2ed6e69 381// Show a search box if all participants don't fit on a single screen.
bc47b706 382if ($participanttable->get_page_size() < $participanttable->totalrows) {
a2ed6e69
SH
383 echo '<form action="index.php" class="searchform"><div><input type="hidden" name="id" value="'.$course->id.'" />';
384 echo '<label for="search">' . get_string('search', 'search') . ' </label>';
385 echo '<input type="text" id="search" name="search" value="'.s($search).'" />&nbsp;<input type="submit" value="'.get_string('search').'" /></div></form>'."\n";
386}
77c645df 387
a2ed6e69 388echo '</div>'; // Userlist.
f9903ed0 389
a78ed71c
DW
390$enrolrenderer = $PAGE->get_renderer('core_enrol');
391echo '<div class="pull-right">';
392foreach ($enrolbuttons as $enrolbutton) {
393 echo $enrolrenderer->render($enrolbutton);
394}
395echo '</div>';
396
a2ed6e69 397echo $OUTPUT->footer();