MDL-29602 accesslib improvements
Refactoring and improvements of the accesslib.php library including prevention of access for not-logged-in users when forcelogin enabled, improved context caching, OOP refactoring of contexts, fixed context loading, deduplication of role definitions in user sessions, installation improvements, decoupling of enrolment checking from capability loading, added detection of deleted and non-existent users in has_capability(), new function accesslib test, auth and enrol upgrade notes. More details are available in tracker subtasks.
This commit is contained in:
@@ -65,13 +65,15 @@ if ($requestedqtype) {
|
||||
|
||||
// Get the question counts, and all the context information, for each
|
||||
// context. That is, rows of these results can be used as $context objects.
|
||||
$ctxpreload = context_helper::get_preload_record_columns_sql('con');
|
||||
$ctxgroupby = implode(',', array_keys(context_helper::get_preload_record_columns('con')));
|
||||
$counts = $DB->get_records_sql("
|
||||
SELECT qc.contextid, count(1) as numquestions, sum(hidden) as numhidden, con.id, con.contextlevel, con.instanceid, con.path, con.depth
|
||||
SELECT qc.contextid, count(1) as numquestions, sum(hidden) as numhidden, $ctxpreload
|
||||
FROM {question} q
|
||||
JOIN {question_categories} qc ON q.category = qc.id
|
||||
JOIN {context} con ON con.id = qc.contextid
|
||||
$sqlqtypetest
|
||||
GROUP BY contextid, con.id, con.contextlevel, con.instanceid, con.path, con.depth
|
||||
GROUP BY qc.contextid, $ctxgroupby
|
||||
ORDER BY numquestions DESC, numhidden ASC, con.contextlevel ASC, con.id ASC", $params);
|
||||
|
||||
// Print the report heading.
|
||||
@@ -94,8 +96,10 @@ if ($requestedqtype) {
|
||||
$totalhidden = 0;
|
||||
foreach ($counts as $count) {
|
||||
// Work out a link for editing questions in this context.
|
||||
$contextname = print_context_name($count);
|
||||
$url = question_edit_url($count);
|
||||
context_helper::preload_from_record($count);
|
||||
$context = context::instance_by_id($count->contextid);
|
||||
$contextname = $context->get_context_name();
|
||||
$url = question_edit_url($context);
|
||||
if ($url) {
|
||||
$contextname = '<a href="' . $url . '" title="' .
|
||||
get_string('editquestionshere', 'report_questioninstances') .
|
||||
|
||||
@@ -96,7 +96,8 @@ foreach ($contexts as $conid => $con) {
|
||||
|
||||
/// Put the contexts into a tree structure.
|
||||
foreach ($contexts as $conid => $con) {
|
||||
$parentcontextid = get_parent_contextid($con);
|
||||
$context = context::instance_by_id($conid);
|
||||
$parentcontextid = get_parent_contextid($context);
|
||||
if ($parentcontextid) {
|
||||
$contexts[$parentcontextid]->children[] = $conid;
|
||||
}
|
||||
@@ -156,13 +157,13 @@ function print_report_tree($contextid, $contexts, $systemcontext, $fullname) {
|
||||
}
|
||||
|
||||
// Pull the current context into an array for convinience.
|
||||
$context = $contexts[$contextid];
|
||||
$context = context::instance_by_id($contextid);
|
||||
|
||||
// Print the context name.
|
||||
echo $OUTPUT->heading(print_context_name($contexts[$contextid]), 4, 'contextname');
|
||||
echo $OUTPUT->heading($context->get_context_name(), 4, 'contextname');
|
||||
|
||||
// If there are any role assignments here, print them.
|
||||
foreach ($context->roleassignments as $ra) {
|
||||
foreach ($contexts[$contextid]->roleassignments as $ra) {
|
||||
$value = $ra->contextid . ',' . $ra->roleid;
|
||||
$inputid = 'unassign' . $value;
|
||||
|
||||
|
||||
@@ -138,7 +138,8 @@ if ($capability) {
|
||||
|
||||
// Put the contexts into a tree structure.
|
||||
foreach ($contexts as $conid => $con) {
|
||||
$parentcontextid = get_parent_contextid($con);
|
||||
$context = context::instance_by_id($conid);
|
||||
$parentcontextid = get_parent_contextid($context);
|
||||
if ($parentcontextid) {
|
||||
$contexts[$parentcontextid]->children[] = $conid;
|
||||
}
|
||||
@@ -196,7 +197,8 @@ function print_report_tree($contextid, $contexts, $allroles) {
|
||||
$url = "$CFG->wwwroot/$CFG->admin/roles/override.php?contextid=$contextid";
|
||||
$title = get_string('changeoverrides', 'tool_capability');
|
||||
}
|
||||
echo '<h3><a href="' . $url . '" title="' . $title . '">', print_context_name($contexts[$contextid]), '</a></h3>';
|
||||
$context = context::instance_by_id($contextid);
|
||||
echo '<h3><a href="' . $url . '" title="' . $title . '">', $context->get_context_name(), '</a></h3>';
|
||||
|
||||
// If there are any role overrides here, print them.
|
||||
if (!empty($contexts[$contextid]->rolecapabilities)) {
|
||||
|
||||
@@ -39,7 +39,9 @@
|
||||
|
||||
if ($shibbolethauth->user_login($frm->username, $frm->password)) {
|
||||
|
||||
$USER = authenticate_user_login($frm->username, $frm->password);
|
||||
$user = authenticate_user_login($frm->username, $frm->password);
|
||||
enrol_check_plugins($user);
|
||||
session_set_user($user);
|
||||
|
||||
$USER->loggedin = true;
|
||||
$USER->site = $CFG->wwwroot; // for added security, store the site in the
|
||||
@@ -75,9 +77,6 @@
|
||||
}
|
||||
}
|
||||
|
||||
enrol_check_plugins($USER);
|
||||
load_all_capabilities(); /// This is what lets the user do anything on the site :-)
|
||||
|
||||
redirect($urltogo);
|
||||
|
||||
exit;
|
||||
|
||||
@@ -0,0 +1,10 @@
|
||||
This files describes API changes in /auth/* - plugins,
|
||||
information provided here is intended especially for developers.
|
||||
|
||||
=== 2.2 ===
|
||||
|
||||
required changes in code:
|
||||
* the correct sequence to set up global $USER is:
|
||||
$user = get_complete_user_data('username', $username); // or $user = authenticate_user_login()
|
||||
enrol_check_plugins($user);
|
||||
session_set_user($user);
|
||||
+2
-2
@@ -143,9 +143,9 @@ if (!empty($entry->id)) {
|
||||
if ($CFG->useblogassociations && ($blogassociations = $DB->get_records('blog_association', array('blogid' => $entry->id)))) {
|
||||
|
||||
foreach ($blogassociations as $assocrec) {
|
||||
$contextrec = $DB->get_record('context', array('id' => $assocrec->contextid));
|
||||
$context = get_context_instance_by_id($assocrec->contextid);
|
||||
|
||||
switch ($contextrec->contextlevel) {
|
||||
switch ($context->contextlevel) {
|
||||
case CONTEXT_COURSE:
|
||||
$entry->courseassoc = $assocrec->contextid;
|
||||
break;
|
||||
|
||||
+4
-4
@@ -95,7 +95,7 @@ class blog_edit_form extends moodleform {
|
||||
$a->modname = $mod->name;
|
||||
$context = get_context_instance(CONTEXT_MODULE, $modid);
|
||||
} else {
|
||||
$context = $DB->get_record('context', array('id' => $entry->modassoc));
|
||||
$context = get_context_instance_by_id($entry->modassoc);
|
||||
$cm = $DB->get_record('course_modules', array('id' => $context->instanceid));
|
||||
$a = new stdClass();
|
||||
$a->modtype = $DB->get_field('modules', 'name', array('id' => $cm->module));
|
||||
@@ -134,7 +134,7 @@ class blog_edit_form extends moodleform {
|
||||
|
||||
// validate course association
|
||||
if (!empty($data['courseassoc']) && has_capability('moodle/blog:associatecourse', $sitecontext)) {
|
||||
$coursecontext = $DB->get_record('context', array('id' => $data['courseassoc'], 'contextlevel' => CONTEXT_COURSE));
|
||||
$coursecontext = get_context_instance(CONTEXT_COURSE, $data['courseassoc']);
|
||||
|
||||
if ($coursecontext) {
|
||||
if (!is_enrolled($coursecontext) and !is_viewing($coursecontext)) {
|
||||
@@ -149,12 +149,12 @@ class blog_edit_form extends moodleform {
|
||||
if (!empty($data['modassoc'])) {
|
||||
$modcontextid = $data['modassoc'];
|
||||
|
||||
$modcontext = $DB->get_record('context', array('id' => $modcontextid, 'contextlevel' => CONTEXT_MODULE));
|
||||
$modcontext = get_context_instance(CONTEXT_MODULE, $modcontextid);
|
||||
|
||||
if ($modcontext) {
|
||||
// get context of the mod's course
|
||||
$path = explode('/', $modcontext->path);
|
||||
$coursecontext = $DB->get_record('context', array('id' => $path[(count($path) - 2)]));
|
||||
$coursecontext = get_context_instance_by_id($path[(count($path) - 2)]);
|
||||
|
||||
// ensure only one course is associated
|
||||
if (!empty($data['courseassoc'])) {
|
||||
|
||||
+7
-7
@@ -247,10 +247,10 @@ class blog_entry {
|
||||
|
||||
// First find and show the associated course
|
||||
foreach ($blogassociations as $assocrec) {
|
||||
$contextrec = $DB->get_record('context', array('id' => $assocrec->contextid));
|
||||
if ($contextrec->contextlevel == CONTEXT_COURSE) {
|
||||
$assocurl = new moodle_url('/course/view.php', array('id' => $contextrec->instanceid));
|
||||
$text = $DB->get_field('course', 'shortname', array('id' => $contextrec->instanceid)); //TODO: performance!!!!
|
||||
$context = get_context_instance_by_id($assocrec->contextid);
|
||||
if ($context->contextlevel == CONTEXT_COURSE) {
|
||||
$assocurl = new moodle_url('/course/view.php', array('id' => $context->instanceid));
|
||||
$text = $DB->get_field('course', 'shortname', array('id' => $context->instanceid)); //TODO: performance!!!!
|
||||
$assocstr .= $OUTPUT->action_icon($assocurl, new pix_icon('i/course', $text), null, array(), true);
|
||||
$hascourseassocs = true;
|
||||
$assoctype = get_string('course');
|
||||
@@ -259,15 +259,15 @@ class blog_entry {
|
||||
|
||||
// Now show mod association
|
||||
foreach ($blogassociations as $assocrec) {
|
||||
$contextrec = $DB->get_record('context', array('id' => $assocrec->contextid));
|
||||
$context = get_context_instance_by_id($assocrec->contextid);
|
||||
|
||||
if ($contextrec->contextlevel == CONTEXT_MODULE) {
|
||||
if ($context->contextlevel == CONTEXT_MODULE) {
|
||||
if ($hascourseassocs) {
|
||||
$assocstr .= ', ';
|
||||
$hascourseassocs = false;
|
||||
}
|
||||
|
||||
$modinfo = $DB->get_record('course_modules', array('id' => $contextrec->instanceid));
|
||||
$modinfo = $DB->get_record('course_modules', array('id' => $context->instanceid));
|
||||
$modname = $DB->get_field('modules', 'name', array('id' => $modinfo->module));
|
||||
|
||||
$assocurl = new moodle_url('/mod/'.$modname.'/view.php', array('id' => $modinfo->id));
|
||||
|
||||
+2
-2
@@ -77,7 +77,7 @@ class enrol_guest_plugin extends enrol_plugin {
|
||||
if (empty($instance->password)) {
|
||||
// Temporarily assign them some guest role for this context
|
||||
$context = get_context_instance(CONTEXT_COURSE, $instance->courseid);
|
||||
$USER->access = load_temp_role($context, $CFG->guestroleid, $USER->access);
|
||||
load_temp_course_role($context, $CFG->guestroleid);
|
||||
return ENROL_REQUIRE_LOGIN_CACHE_PERIOD + time();
|
||||
}
|
||||
|
||||
@@ -131,7 +131,7 @@ class enrol_guest_plugin extends enrol_plugin {
|
||||
|
||||
// add guest role
|
||||
$context = get_context_instance(CONTEXT_COURSE, $instance->courseid);
|
||||
$USER->access = load_temp_role($context, $CFG->guestroleid, $USER->access);
|
||||
load_temp_course_role($context, $CFG->guestroleid);
|
||||
|
||||
// go to the originally requested page
|
||||
if (!empty($SESSION->wantsurl)) {
|
||||
|
||||
@@ -38,9 +38,6 @@ $context = get_context_instance(CONTEXT_COURSE, $course->id, MUST_EXIST);
|
||||
|
||||
require_login();
|
||||
|
||||
// Refreshing enrolment data in the USER session
|
||||
load_all_capabilities();
|
||||
|
||||
if ($SESSION->wantsurl) {
|
||||
$destination = $SESSION->wantsurl;
|
||||
unset($SESSION->wantsurl);
|
||||
|
||||
@@ -0,0 +1,8 @@
|
||||
This files describes API changes in /enrol/* - plugins,
|
||||
information provided here is intended especially for developers.
|
||||
|
||||
=== 2.2 ===
|
||||
|
||||
required changes in code:
|
||||
* load_temp_role() is deprecated, use load_temp_course_role() instead, temp role not loaded
|
||||
* remove_temp_role() is deprecated, use remove_temp_course_roles() instead
|
||||
+3533
-2645
File diff suppressed because it is too large
Load Diff
+5
-1
@@ -1014,7 +1014,11 @@ function fix_course_sortorder() {
|
||||
|
||||
// now fix the paths and depths in context table if needed
|
||||
if ($fixcontexts) {
|
||||
rebuild_contexts($fixcontexts);
|
||||
foreach ($fixcontexts as $fixcontext) {
|
||||
$fixcontext->reset_paths(false);
|
||||
}
|
||||
context_helper::build_all_paths(false);
|
||||
unset($fixcontexts);
|
||||
}
|
||||
|
||||
// release memory
|
||||
|
||||
+49
-20
@@ -29,14 +29,17 @@ defined('MOODLE_INTERNAL') || die();
|
||||
function xmldb_main_install() {
|
||||
global $CFG, $DB, $SITE;
|
||||
|
||||
/// make sure system context exists
|
||||
$syscontext = get_system_context(false);
|
||||
if ($syscontext->id != 1) {
|
||||
/// Make sure system context exists
|
||||
$syscontext = context_system::instance(0, MUST_EXIST, false);
|
||||
if ($syscontext->id != SYSCONTEXTID) {
|
||||
throw new moodle_exception('generalexceptionmessage', 'error', '', 'Unexpected new system context id!');
|
||||
}
|
||||
|
||||
|
||||
/// create site course
|
||||
/// Create site course
|
||||
if ($DB->record_exists('course', array())) {
|
||||
throw new moodle_exception('generalexceptionmessage', 'error', '', 'Can not create frontpage course, courses already exist.');
|
||||
}
|
||||
$newsite = new stdClass();
|
||||
$newsite->fullname = '';
|
||||
$newsite->shortname = '';
|
||||
@@ -48,18 +51,38 @@ function xmldb_main_install() {
|
||||
$newsite->timecreated = time();
|
||||
$newsite->timemodified = $newsite->timecreated;
|
||||
|
||||
$newsite->id = $DB->insert_record('course', $newsite);
|
||||
if (defined('SITEID')) {
|
||||
$newsite->id = SITEID;
|
||||
$DB->import_record('course', $newsite);
|
||||
$DB->get_manager()->reset_sequence('course');
|
||||
} else {
|
||||
$newsite->id = $DB->insert_record('course', $newsite);
|
||||
define('SITEID', $newsite->id);
|
||||
}
|
||||
$SITE = get_site();
|
||||
if ($newsite->id != 1 or $SITE->id != 1) {
|
||||
if ($newsite->id != $SITE->id) {
|
||||
throw new moodle_exception('generalexceptionmessage', 'error', '', 'Unexpected new site course id!');
|
||||
}
|
||||
// Make sure site course context exists
|
||||
context_course::instance($SITE->id);
|
||||
// Update the global frontpage cache
|
||||
$SITE = $DB->get_record('course', array('id'=>$newsite->id), '*', MUST_EXIST);
|
||||
|
||||
|
||||
/// make sure site course context exists
|
||||
get_context_instance(CONTEXT_COURSE, $SITE->id);
|
||||
/// Create default course category
|
||||
if ($DB->record_exists('course_categories', array())) {
|
||||
throw new moodle_exception('generalexceptionmessage', 'error', '', 'Can not create default course category, categories already exist.');
|
||||
}
|
||||
$cat = new stdClass();
|
||||
$cat->name = get_string('miscellaneous');
|
||||
$cat->depth = 1;
|
||||
$cat->sortorder = MAX_COURSES_IN_CATEGORY;
|
||||
$cat->timemodified = time();
|
||||
$catid = $DB->insert_record('course_categories', $cat);
|
||||
$DB->set_field('course_categories', 'path', '/'.$catid, array('id'=>$catid));
|
||||
// Make sure category context exists
|
||||
context_coursecat::instance($catid);
|
||||
|
||||
/// create default course category
|
||||
$cat = get_course_category();
|
||||
|
||||
$defaults = array(
|
||||
'rolesactive' => '0', // marks fully set up system
|
||||
@@ -82,7 +105,7 @@ function xmldb_main_install() {
|
||||
}
|
||||
|
||||
|
||||
/// bootstrap mnet
|
||||
/// Bootstrap mnet
|
||||
$mnethost = new stdClass();
|
||||
$mnethost->wwwroot = $CFG->wwwroot;
|
||||
$mnethost->name = '';
|
||||
@@ -137,7 +160,10 @@ function xmldb_main_install() {
|
||||
$mnetallhosts->id = $DB->insert_record('mnet_host', $mnetallhosts, true);
|
||||
set_config('mnet_all_hosts_id', $mnetallhosts->id);
|
||||
|
||||
/// Create guest record - do not assign any role, guest user get's the default guest role automatically on the fly
|
||||
/// Create guest record - do not assign any role, guest user gets the default guest role automatically on the fly
|
||||
if ($DB->record_exists('user', array())) {
|
||||
throw new moodle_exception('generalexceptionmessage', 'error', '', 'Can not create default users, users already exist.');
|
||||
}
|
||||
$guest = new stdClass();
|
||||
$guest->auth = 'manual';
|
||||
$guest->username = 'guest';
|
||||
@@ -156,6 +182,8 @@ function xmldb_main_install() {
|
||||
}
|
||||
// Store guest id
|
||||
set_config('siteguest', $guest->id);
|
||||
// Make sure user context exists
|
||||
context_user::instance($guest->id);
|
||||
|
||||
|
||||
/// Now create admin user
|
||||
@@ -176,8 +204,10 @@ function xmldb_main_install() {
|
||||
if ($admin->id != 2) {
|
||||
throw new moodle_exception('generalexceptionmessage', 'error', '', 'Unexpected new admin user id!');
|
||||
}
|
||||
/// Store list of admins
|
||||
// Store list of admins
|
||||
set_config('siteadmins', $admin->id);
|
||||
// Make sure user context exists
|
||||
context_user::instance($admin->id);
|
||||
|
||||
|
||||
/// Install the roles system.
|
||||
@@ -264,17 +294,16 @@ function xmldb_main_install() {
|
||||
require_once($CFG->libdir . '/licenselib.php');
|
||||
license_manager::install_licenses();
|
||||
|
||||
/// Add two lines of data into this new table
|
||||
// Init profile pages defaults
|
||||
if ($DB->record_exists('my_pages', array())) {
|
||||
throw new moodle_exception('generalexceptionmessage', 'error', '', 'Can not create default profile pages, records already exist.');
|
||||
}
|
||||
$mypage = new stdClass();
|
||||
$mypage->userid = NULL;
|
||||
$mypage->name = '__default';
|
||||
$mypage->private = 0;
|
||||
$mypage->sortorder = 0;
|
||||
if (!$DB->record_exists('my_pages', array('userid'=>NULL, 'private'=>0))) {
|
||||
$DB->insert_record('my_pages', $mypage);
|
||||
}
|
||||
$DB->insert_record('my_pages', $mypage);
|
||||
$mypage->private = 1;
|
||||
if (!$DB->record_exists('my_pages', array('userid'=>NULL, 'private'=>1))) {
|
||||
$DB->insert_record('my_pages', $mypage);
|
||||
}
|
||||
$DB->insert_record('my_pages', $mypage);
|
||||
}
|
||||
|
||||
+7
-20
@@ -280,28 +280,28 @@ function isteacher() {
|
||||
* @deprecated
|
||||
*/
|
||||
function isteacherinanycourse() {
|
||||
error('Function isteacherinanycourse() was removed, please use capabilities instead!');
|
||||
throw new coding_Exception('Function isteacherinanycourse() was removed, please use capabilities instead!');
|
||||
}
|
||||
|
||||
/**
|
||||
* @deprecated
|
||||
*/
|
||||
function get_guest() {
|
||||
error('Function get_guest() was removed, please use capabilities instead!');
|
||||
throw new coding_Exception('Function get_guest() was removed, please use capabilities instead!');
|
||||
}
|
||||
|
||||
/**
|
||||
* @deprecated
|
||||
*/
|
||||
function isguest() {
|
||||
error('Function isguest() was removed, please use capabilities instead!');
|
||||
throw new coding_Exception('Function isguest() was removed, please use capabilities instead!');
|
||||
}
|
||||
|
||||
/**
|
||||
* @deprecated
|
||||
*/
|
||||
function get_teacher() {
|
||||
error('Function get_teacher() was removed, please use capabilities instead!');
|
||||
throw new coding_Exception('Function get_teacher() was removed, please use capabilities instead!');
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -371,15 +371,7 @@ function get_recent_enrolments($courseid, $timestart) {
|
||||
* @return object
|
||||
*/
|
||||
function make_context_subobj($rec) {
|
||||
$ctx = new StdClass;
|
||||
$ctx->id = $rec->ctxid; unset($rec->ctxid);
|
||||
$ctx->path = $rec->ctxpath; unset($rec->ctxpath);
|
||||
$ctx->depth = $rec->ctxdepth; unset($rec->ctxdepth);
|
||||
$ctx->contextlevel = $rec->ctxlevel; unset($rec->ctxlevel);
|
||||
$ctx->instanceid = $rec->id;
|
||||
|
||||
$rec->context = $ctx;
|
||||
return $rec;
|
||||
throw new coding_Exception('make_context_subobj() was removed, use new context preloading');
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -395,10 +387,7 @@ function make_context_subobj($rec) {
|
||||
* for this thing.
|
||||
*/
|
||||
function is_context_subobj_valid($rec, $contextlevel) {
|
||||
return isset($rec->context) && isset($rec->context->id) &&
|
||||
isset($rec->context->path) && isset($rec->context->depth) &&
|
||||
isset($rec->context->contextlevel) && isset($rec->context->instanceid) &&
|
||||
$rec->context->contextlevel == $contextlevel && $rec->context->instanceid == $rec->id;
|
||||
throw new coding_Exception('is_context_subobj_valid() was removed, use new context preloading');
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -415,9 +404,7 @@ function is_context_subobj_valid($rec, $contextlevel) {
|
||||
* @param integer $contextlevel the type of thing $rec is, one of the CONTEXT_... constants.
|
||||
*/
|
||||
function ensure_context_subobj_present(&$rec, $contextlevel) {
|
||||
if (!is_context_subobj_valid($rec, $contextlevel)) {
|
||||
$rec->context = get_context_instance($contextlevel, $rec->id);
|
||||
}
|
||||
throw new coding_Exception('ensure_context_subobj_present() was removed, use new context preloading');
|
||||
}
|
||||
|
||||
########### FROM weblib.php ##########################################################################
|
||||
|
||||
+6
-4
@@ -188,7 +188,9 @@ function enrol_is_enabled($enrol) {
|
||||
* Check all the login enrolment information for the given user object
|
||||
* by querying the enrolment plugins
|
||||
*
|
||||
* @param object $user
|
||||
* This function may be very slow, use only once after log-in or login-as.
|
||||
*
|
||||
* @param stdClass $user
|
||||
* @return void
|
||||
*/
|
||||
function enrol_check_plugins($user) {
|
||||
@@ -201,7 +203,7 @@ function enrol_check_plugins($user) {
|
||||
|
||||
if (is_siteadmin()) {
|
||||
// no sync for admin user, please use admin accounts only for admin tasks like the unix root user!
|
||||
// if plugin fails on sync admins need to be able to log in
|
||||
// if plugin fails on sync admins need to be able to log in and fix the settings
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -1150,7 +1152,7 @@ abstract class enrol_plugin {
|
||||
}
|
||||
if (isset($USER->enrol['tempguest'][$courseid])) {
|
||||
unset($USER->enrol['tempguest'][$courseid]);
|
||||
$USER->access = remove_temp_roles($context, $USER->access);
|
||||
remove_temp_course_roles($context);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1272,7 +1274,7 @@ abstract class enrol_plugin {
|
||||
}
|
||||
if (isset($USER->enrol['tempguest'][$courseid])) {
|
||||
unset($USER->enrol['tempguest'][$courseid]);
|
||||
$USER->access = remove_temp_roles($context, $USER->access);
|
||||
remove_temp_course_roles($context);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+9
-5
@@ -2790,7 +2790,7 @@ function require_login($courseorid = NULL, $autologinguest = true, $cm = NULL, $
|
||||
} else {
|
||||
//expired
|
||||
unset($USER->enrol['tempguest'][$course->id]);
|
||||
$USER->access = remove_temp_roles($coursecontext, $USER->access);
|
||||
remove_temp_course_roles($coursecontext);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2817,7 +2817,7 @@ function require_login($courseorid = NULL, $autologinguest = true, $cm = NULL, $
|
||||
$access = true;
|
||||
|
||||
// remove traces of previous temp guest access
|
||||
$USER->access = remove_temp_roles($coursecontext, $USER->access);
|
||||
remove_temp_course_roles($coursecontext);
|
||||
|
||||
} else {
|
||||
$instances = $DB->get_records('enrol', array('courseid'=>$course->id, 'status'=>ENROL_INSTANCE_ENABLED), 'sortorder, id ASC');
|
||||
@@ -2831,7 +2831,7 @@ function require_login($courseorid = NULL, $autologinguest = true, $cm = NULL, $
|
||||
$until = $enrols[$instance->enrol]->try_autoenrol($instance);
|
||||
if ($until !== false) {
|
||||
$USER->enrol['enrolled'][$course->id] = $until;
|
||||
$USER->access = remove_temp_roles($coursecontext, $USER->access);
|
||||
remove_temp_course_roles($coursecontext);
|
||||
$access = true;
|
||||
break;
|
||||
}
|
||||
@@ -3031,6 +3031,7 @@ function require_user_key_login($script, $instance=null) {
|
||||
}
|
||||
|
||||
/// emulate normal session
|
||||
enrol_check_plugins($user);
|
||||
session_set_user($user);
|
||||
|
||||
/// note we are not using normal login
|
||||
@@ -3882,12 +3883,15 @@ function complete_user_login($user) {
|
||||
// this helps prevent session fixation attacks from the same domain
|
||||
session_regenerate_id(true);
|
||||
|
||||
// let enrol plugins deal with new enrolments if necessary
|
||||
enrol_check_plugins($user);
|
||||
|
||||
// check enrolments, load caps and setup $USER object
|
||||
session_set_user($user);
|
||||
|
||||
// reload preferences from DB
|
||||
unset($user->preference);
|
||||
check_user_preferences_loaded($user);
|
||||
unset($USER->preference);
|
||||
check_user_preferences_loaded($USER);
|
||||
|
||||
// update login times
|
||||
update_user_login_times();
|
||||
|
||||
@@ -2868,7 +2868,7 @@ class settings_navigation extends navigation_node {
|
||||
$context = $this->context;
|
||||
if ($context->contextlevel == CONTEXT_BLOCK) {
|
||||
$this->load_block_settings();
|
||||
$context = $DB->get_record_sql('SELECT ctx.* FROM {block_instances} bi LEFT JOIN {context} ctx ON ctx.id=bi.parentcontextid WHERE bi.id=?', array($context->instanceid));
|
||||
$context = $context->get_parent_context();
|
||||
}
|
||||
|
||||
switch ($context->contextlevel) {
|
||||
|
||||
+6
-6
@@ -894,7 +894,8 @@ function get_moodle_cookie() {
|
||||
|
||||
/**
|
||||
* Setup $USER object - called during login, loginas, etc.
|
||||
* Preloads capabilities and checks enrolment plugins
|
||||
*
|
||||
* Call sync_user_enrolments() manually after log-in, or log-in-as.
|
||||
*
|
||||
* @param stdClass $user full user record object
|
||||
* @return void
|
||||
@@ -902,11 +903,6 @@ function get_moodle_cookie() {
|
||||
function session_set_user($user) {
|
||||
$_SESSION['USER'] = $user;
|
||||
unset($_SESSION['USER']->description); // conserve memory
|
||||
if (!isset($_SESSION['USER']->access)) {
|
||||
// check enrolments and load caps only once
|
||||
enrol_check_plugins($_SESSION['USER']);
|
||||
load_all_capabilities();
|
||||
}
|
||||
sesskey(); // init session key
|
||||
}
|
||||
|
||||
@@ -950,6 +946,10 @@ function session_loginas($userid, $context) {
|
||||
$user = get_complete_user_data('id', $userid);
|
||||
$user->realuser = $_SESSION['REALUSER']->id;
|
||||
$user->loginascontext = $context;
|
||||
|
||||
// let enrol plugins deal with new enrolments if necessary
|
||||
enrol_check_plugins($user);
|
||||
// set up global $USER
|
||||
session_set_user($user);
|
||||
}
|
||||
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,382 +0,0 @@
|
||||
<?php
|
||||
/**
|
||||
* Unit tests for (some of) ../accesslib.php.
|
||||
*
|
||||
* @copyright © 2006 The Open University
|
||||
* @author [email protected]
|
||||
* @license http://www.gnu.org/copyleft/gpl.html GNU Public License
|
||||
* @package moodlecore
|
||||
*/
|
||||
|
||||
if (!defined('MOODLE_INTERNAL')) {
|
||||
die('Direct access to this script is forbidden.'); /// It must be included from a Moodle page
|
||||
}
|
||||
|
||||
class accesslib_test extends UnitTestCaseUsingDatabase {
|
||||
|
||||
public static $includecoverage = array('lib/accesslib.php');
|
||||
|
||||
function test_get_parent_contexts() {
|
||||
$context = get_context_instance(CONTEXT_SYSTEM);
|
||||
$this->assertEqual(get_parent_contexts($context), array());
|
||||
|
||||
$context = new stdClass;
|
||||
$context->path = '/1/25';
|
||||
$this->assertEqual(get_parent_contexts($context), array(1));
|
||||
|
||||
$context = new stdClass;
|
||||
$context->path = '/1/123/234/345/456';
|
||||
$this->assertEqual(get_parent_contexts($context), array(345, 234, 123, 1));
|
||||
}
|
||||
|
||||
function test_get_parent_contextid() {
|
||||
$context = get_context_instance(CONTEXT_SYSTEM);
|
||||
$this->assertFalse(get_parent_contextid($context));
|
||||
|
||||
$context = new stdClass;
|
||||
$context->path = '/1/25';
|
||||
$this->assertEqual(get_parent_contextid($context), 1);
|
||||
|
||||
$context = new stdClass;
|
||||
$context->path = '/1/123/234/345/456';
|
||||
$this->assertEqual(get_parent_contextid($context), 345);
|
||||
}
|
||||
|
||||
function test_get_users_by_capability() {
|
||||
global $CFG;
|
||||
|
||||
$tablenames = array('capabilities', 'context', 'role', 'role_capabilities',
|
||||
'role_allow_assign', 'role_allow_override', 'role_assignments', 'role_context_levels',
|
||||
'user', 'groups_members', 'cache_flags', 'events_handlers', 'user_lastaccess', 'course');
|
||||
$this->create_test_tables($tablenames, 'lib');
|
||||
|
||||
accesslib_clear_all_caches_for_unit_testing();
|
||||
$this->switch_to_test_db();
|
||||
$this->switch_to_test_cfg();
|
||||
|
||||
$course = new stdClass();
|
||||
$course->category = 0;
|
||||
$this->testdb->insert_record('course', $course);
|
||||
$syscontext = get_system_context(false);
|
||||
|
||||
/// Install the roles system.
|
||||
$coursecreatorrole = create_role(get_string('coursecreators'), 'coursecreator',
|
||||
get_string('coursecreatorsdescription'), 'coursecreator');
|
||||
$editteacherrole = create_role(get_string('defaultcourseteacher'), 'editingteacher',
|
||||
get_string('defaultcourseteacherdescription'), 'editingteacher');
|
||||
$noneditteacherrole = create_role(get_string('noneditingteacher'), 'teacher',
|
||||
get_string('noneditingteacherdescription'), 'teacher');
|
||||
$studentrole = create_role(get_string('defaultcoursestudent'), 'student',
|
||||
get_string('defaultcoursestudentdescription'), 'student');
|
||||
$guestrole = create_role(get_string('guest'), 'guest',
|
||||
get_string('guestdescription'), 'guest');
|
||||
$userrole = create_role(get_string('authenticateduser'), 'user',
|
||||
get_string('authenticateduserdescription'), 'user');
|
||||
|
||||
/// Now is the correct moment to install capabilities - after creation of legacy roles, but before assigning of roles
|
||||
update_capabilities('moodle');
|
||||
update_capabilities('mod_forum');
|
||||
update_capabilities('mod_quiz');
|
||||
|
||||
// Create some nested contexts. instanceid does not matter for this. Just
|
||||
// ensure we don't violate any unique keys by using an unlikely number.
|
||||
// We will fix paths in a second.
|
||||
$contexts = $this->load_test_data('context',
|
||||
array('contextlevel', 'instanceid', 'path', 'depth'), array(
|
||||
1 => array(40, 666, '', 2),
|
||||
2 => array(50, 666, '', 3),
|
||||
3 => array(70, 666, '', 4),
|
||||
));
|
||||
$contexts[0] = $syscontext;
|
||||
$contexts[1]->path = $contexts[0]->path . '/' . $contexts[1]->id;
|
||||
$this->testdb->set_field('context', 'path', $contexts[1]->path, array('id' => $contexts[1]->id));
|
||||
$contexts[2]->path = $contexts[1]->path . '/' . $contexts[2]->id;
|
||||
$this->testdb->set_field('context', 'path', $contexts[2]->path, array('id' => $contexts[2]->id));
|
||||
$contexts[3]->path = $contexts[2]->path . '/' . $contexts[3]->id;
|
||||
$this->testdb->set_field('context', 'path', $contexts[3]->path, array('id' => $contexts[3]->id));
|
||||
|
||||
// Now make some test users.
|
||||
$users = $this->load_test_data('user',
|
||||
array('username', 'confirmed', 'deleted'), array(
|
||||
'a' => array('a', 1, 0),
|
||||
'cc' => array('cc', 1, 0),
|
||||
't1' => array('t1', 1, 0),
|
||||
's1' => array('s1', 1, 0),
|
||||
's2' => array('s2', 1, 0),
|
||||
'del' => array('del', 1, 1),
|
||||
'unc' => array('unc', 0, 0),
|
||||
));
|
||||
|
||||
// Get some of the standard roles.
|
||||
$creator = $this->testdb->get_record('role', array('shortname' => 'coursecreator'));
|
||||
$teacher = $this->testdb->get_record('role', array('shortname' => 'editingteacher'));
|
||||
$student = $this->testdb->get_record('role', array('shortname' => 'student'));
|
||||
$authuser = $this->testdb->get_record('role', array('shortname' => 'user'));
|
||||
|
||||
// And some role assignments.
|
||||
$ras = $this->load_test_data('role_assignments',
|
||||
array('userid', 'roleid', 'contextid'), array(
|
||||
'cc' => array($users['cc']->id, $creator->id, $contexts[1]->id),
|
||||
't1' => array($users['t1']->id, $teacher->id, $contexts[2]->id),
|
||||
's1' => array($users['s1']->id, $student->id, $contexts[2]->id),
|
||||
's2' => array($users['s2']->id, $student->id, $contexts[2]->id),
|
||||
));
|
||||
|
||||
// And make user a into admin
|
||||
$CFG->siteadmins = $users['a']->id;
|
||||
$CFG->defaultuserroleid = $userrole;
|
||||
|
||||
// And some group memebership.
|
||||
$gms = $this->load_test_data('groups_members',
|
||||
array('userid', 'groupid'), array(
|
||||
array($users['t1']->id, 666),
|
||||
array($users['s1']->id, 666),
|
||||
array($users['s2']->id, 667),
|
||||
));
|
||||
|
||||
// Test some simple cases - check that looking in coruse and module contextlevel gives the same answer.
|
||||
foreach (array(2, 3) as $conindex) {
|
||||
$results = get_users_by_capability($contexts[$conindex], 'mod/forum:replypost');
|
||||
// note: admin accounts are never returned, so no admin return here
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(
|
||||
array($users['t1']->id, $users['s1']->id, $users['s2']->id)),
|
||||
array_map(create_function('$o', 'return $o->id;'),
|
||||
$results));
|
||||
// Paging.
|
||||
$firstuser = reset($results);
|
||||
$this->assertEqual(array($firstuser->id => $firstuser), get_users_by_capability($contexts[$conindex], 'mod/forum:replypost', '', '', 0, 1));
|
||||
$seconduser = next($results);
|
||||
$this->assertEqual(array($seconduser->id => $seconduser), get_users_by_capability($contexts[$conindex], 'mod/forum:replypost', '', '', 1, 1));
|
||||
// $doanything = false (ignored now)
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(
|
||||
array($users['t1']->id, $users['s1']->id, $users['s2']->id)),
|
||||
array_map(create_function('$o', 'return $o->id;'),
|
||||
get_users_by_capability($contexts[$conindex], 'mod/forum:replypost', '', '', '', '', '', '', false)));
|
||||
// group
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(
|
||||
array($users['t1']->id, $users['s1']->id)),
|
||||
array_map(create_function('$o', 'return $o->id;'),
|
||||
get_users_by_capability($contexts[$conindex], 'mod/forum:replypost', '', '', '', '', 666)));
|
||||
// exceptions
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(
|
||||
array($users['s1']->id, $users['s2']->id)),
|
||||
array_map(create_function('$o', 'return $o->id;'),
|
||||
get_users_by_capability($contexts[$conindex], 'mod/forum:replypost', '', '', '', '', '', array($users['t1']->id))));
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(
|
||||
array($users['s1']->id)),
|
||||
array_map(create_function('$o', 'return $o->id;'),
|
||||
get_users_by_capability($contexts[$conindex], 'mod/forum:replypost', '', '', '', '', 666, array($users['t1']->id))));
|
||||
// $useviewallgroups
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(
|
||||
array($users['t1']->id, $users['s2']->id)),
|
||||
array_map(create_function('$o', 'return $o->id;'),
|
||||
get_users_by_capability($contexts[$conindex], 'mod/forum:replypost', '', '', '', '', 667, '', false, false, true)));
|
||||
// More than one capability.
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(
|
||||
array($users['s1']->id, $users['s2']->id)),
|
||||
array_map(create_function('$o', 'return $o->id;'),
|
||||
get_users_by_capability($contexts[$conindex], array('mod/quiz:attempt', 'mod/quiz:reviewmyattempts'))));
|
||||
}
|
||||
|
||||
// For reference: get_users_by_capability argument order:
|
||||
// $context, $capability, $fields='', $sort='', $limitfrom='', $limitnum='',
|
||||
// $groups='', $exceptions='', $doanything=true, $view=false, $useviewallgroups=false
|
||||
|
||||
// Now add some role overrides.
|
||||
$rcs = $this->load_test_data('role_capabilities',
|
||||
array('capability', 'roleid', 'contextid', 'permission'), array(
|
||||
array('mod/forum:replypost', $student->id, $contexts[1]->id, CAP_PREVENT),
|
||||
array('mod/forum:replypost', $student->id, $contexts[3]->id, CAP_ALLOW),
|
||||
array('mod/quiz:attempt', $student->id, $contexts[2]->id, CAP_PREVENT),
|
||||
array('mod/forum:startdiscussion', $student->id, $contexts[1]->id, CAP_PROHIBIT),
|
||||
array('mod/forum:startdiscussion', $student->id, $contexts[3]->id, CAP_ALLOW),
|
||||
array('mod/forum:viewrating', $authuser->id, $contexts[1]->id, CAP_PROHIBIT),
|
||||
array('mod/forum:createattachment', $authuser->id, $contexts[3]->id, CAP_PREVENT),
|
||||
));
|
||||
|
||||
// Now test the overridden cases.
|
||||
// Students prevented at category level, with and without doanything.
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(
|
||||
array($users['t1']->id)),
|
||||
array_map(create_function('$o', 'return $o->id;'),
|
||||
get_users_by_capability($contexts[2], 'mod/forum:replypost')));
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(
|
||||
array($users['t1']->id)),
|
||||
array_map(create_function('$o', 'return $o->id;'),
|
||||
get_users_by_capability($contexts[2], 'mod/forum:replypost', '', '', '', '', '', '', false)));
|
||||
// Students prevented at category level, but re-allowed at module level, with and without doanything.
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(
|
||||
array($users['t1']->id, $users['s1']->id, $users['s2']->id)),
|
||||
array_map(create_function('$o', 'return $o->id;'),
|
||||
get_users_by_capability($contexts[3], 'mod/forum:replypost', '', '', '', '', '', '', false)));
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(
|
||||
array($users['t1']->id, $users['s1']->id, $users['s2']->id)),
|
||||
array_map(create_function('$o', 'return $o->id;'),
|
||||
get_users_by_capability($contexts[3], 'mod/forum:replypost')));
|
||||
// Students prohibited at category level, re-allowed at module level should have no effect.
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(
|
||||
array($users['t1']->id)),
|
||||
array_map(create_function('$o', 'return $o->id;'),
|
||||
get_users_by_capability($contexts[2], 'mod/forum:startdiscussion')));
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(
|
||||
array($users['t1']->id)),
|
||||
array_map(create_function('$o', 'return $o->id;'),
|
||||
get_users_by_capability($contexts[3], 'mod/forum:startdiscussion')));
|
||||
// Prevent on logged-in user should be overridden by student allow.
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(
|
||||
array($users['t1']->id, $users['s1']->id, $users['s2']->id)),
|
||||
array_map(create_function('$o', 'return $o->id;'),
|
||||
get_users_by_capability($contexts[3], 'mod/forum:createattachment')));
|
||||
|
||||
// Prohibit on logged-in user should trump student/teacher allow.
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(
|
||||
array()),
|
||||
array_map(create_function('$o', 'return $o->id;'),
|
||||
get_users_by_capability($contexts[3], 'mod/forum:viewrating')));
|
||||
|
||||
// More than one capability, where students have one, but not the other.
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(
|
||||
array($users['s1']->id, $users['s2']->id)),
|
||||
array_map(create_function('$o', 'return $o->id;'),
|
||||
get_users_by_capability($contexts[3], array('mod/quiz:attempt', 'mod/quiz:reviewmyattempts'), '', '', '', '', '', '', false)));
|
||||
}
|
||||
|
||||
function test_get_switchable_roles() {
|
||||
global $USER;
|
||||
|
||||
$tablenames = array('role' , 'role_capabilities', 'role_assignments', 'role_allow_switch',
|
||||
'capabilities', 'context', 'role_names');
|
||||
$this->create_test_tables($tablenames, 'lib');
|
||||
|
||||
$this->switch_to_test_db();
|
||||
$this->switch_to_test_cfg();
|
||||
|
||||
// Ensure SYSCONTEXTID is set.
|
||||
get_context_instance(CONTEXT_SYSTEM);
|
||||
|
||||
$contexts = $this->load_test_data('context',
|
||||
array('contextlevel', 'instanceid', 'path', 'depth'), array(
|
||||
'sys' => array(CONTEXT_SYSTEM, 0, '/' . SYSCONTEXTID, 1),
|
||||
'cat' => array(CONTEXT_COURSECAT, 66, '/' . SYSCONTEXTID . '/' . (SYSCONTEXTID + 1), 2),
|
||||
'cou' => array(CONTEXT_COURSE, 666, '/' . SYSCONTEXTID . '/' . (SYSCONTEXTID + 1) . '/' . (SYSCONTEXTID + 2), 3),
|
||||
'fp' => array(CONTEXT_COURSE, SITEID, '/' . SYSCONTEXTID . '/' . SITEID, 2)));
|
||||
$this->testdb->set_field('context', 'id', SYSCONTEXTID, array('id' => $contexts['sys']->id));
|
||||
$this->testdb->set_field('context', 'id', SYSCONTEXTID + 1, array('id' => $contexts['cat']->id));
|
||||
$this->testdb->set_field('context', 'id', SYSCONTEXTID + 2, array('id' => $contexts['cou']->id));
|
||||
$syscontext = $contexts['sys'];
|
||||
$syscontext->id = SYSCONTEXTID;
|
||||
$context = $contexts['cou'];
|
||||
$context->id = SYSCONTEXTID + 2;
|
||||
|
||||
$roles = $this->load_test_data('role',
|
||||
array( 'name', 'shortname', 'description', 'sortorder'), array(
|
||||
'r1' => array( 'r1', 'r1', 'not null', 2),
|
||||
'r2' => array( 'r2', 'r2', 'not null', 3),
|
||||
'funny' => array('funny', 'funny', 'not null', 4)));
|
||||
$r1id = $roles['r1']->id;
|
||||
$r2id = $roles['r2']->id;
|
||||
$funnyid = $roles['funny']->id; // strange role
|
||||
|
||||
// Note that get_switchable_roles requires at least one capability for
|
||||
// each role. I am not really clear why it was implemented that way
|
||||
// but this makes the test work.
|
||||
$roles = $this->load_test_data('role_capabilities',
|
||||
array('roleid', 'capability'), array(
|
||||
array($r1id, 'moodle/say:hello'),
|
||||
array($r2id, 'moodle/say:hello'),
|
||||
array($funnyid, 'moodle/say:hello'),
|
||||
));
|
||||
|
||||
$this->load_test_data('role_assignments',
|
||||
array('userid', 'contextid', 'roleid'), array(
|
||||
array( 2, SYSCONTEXTID + 1 , $r1id),
|
||||
array( 3, SYSCONTEXTID + 2 , $r2id)));
|
||||
|
||||
$this->load_test_data('role_allow_switch',
|
||||
array('roleid', 'allowswitch'), array(
|
||||
array( $r1id , $r2id),
|
||||
array( $r2id , $r1id),
|
||||
array( $r2id , $r2id),
|
||||
array( $r2id , $funnyid)));
|
||||
|
||||
// r1 should be able to switch to r2, but this user only has r1 in $context, not $syscontext.
|
||||
$this->switch_global_user_id(2);
|
||||
accesslib_clear_all_caches_for_unit_testing();
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(array()), array_keys(get_switchable_roles($syscontext)));
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(array($r2id)), array_keys(get_switchable_roles($context)));
|
||||
$this->revert_global_user_id();
|
||||
|
||||
// The table says r2 should be able to switch to all of r1, r2 and funny;
|
||||
// this used to be restricted further beyond the switch table (for example
|
||||
// to prevent you switching to roles with doanything) but is not any more
|
||||
// (for example because doanything does not exist).
|
||||
$this->switch_global_user_id(3);
|
||||
accesslib_clear_all_caches_for_unit_testing();
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(array()), array_keys(get_switchable_roles($syscontext)));
|
||||
$this->assert(new ArraysHaveSameValuesExpectation(array($r2id, $r1id, $funnyid)), array_keys(get_switchable_roles($context)));
|
||||
}
|
||||
|
||||
function test_context_cache() {
|
||||
// Create cache, empty
|
||||
$cache = new context_cache();
|
||||
$this->assertEqual(0, $cache->get_approx_count());
|
||||
|
||||
// Put context in cache
|
||||
$context = (object)array('id'=>37,'contextlevel'=>50,'instanceid'=>13);
|
||||
$cache->add($context);
|
||||
$this->assertEqual(1, $cache->get_approx_count());
|
||||
|
||||
// Get context out of cache
|
||||
$this->assertEqual($context, $cache->get(50, 13));
|
||||
$this->assertEqual($context, $cache->get_by_id(37));
|
||||
|
||||
// Try to get context that isn't there
|
||||
$this->assertEqual(false, $cache->get(50, 99));
|
||||
$this->assertEqual(false, $cache->get(99, 13));
|
||||
$this->assertEqual(false, $cache->get_by_id(99));
|
||||
|
||||
// Remove context from cache
|
||||
$cache->remove($context);
|
||||
$this->assertEqual(0, $cache->get_approx_count());
|
||||
$this->assertEqual(false, $cache->get(50, 13));
|
||||
$this->assertEqual(false, $cache->get_by_id(37));
|
||||
|
||||
// Add a stack of contexts to cache
|
||||
for($i=0; $i<context_cache::MAX_SIZE; $i++) {
|
||||
$context = (object)array('id'=>$i, 'contextlevel'=>50,
|
||||
'instanceid'=>$i+1);
|
||||
$cache->add($context);
|
||||
}
|
||||
$this->assertEqual(context_cache::MAX_SIZE, $cache->get_approx_count());
|
||||
|
||||
// Get a random sample from the middle
|
||||
$sample = (object)array(
|
||||
'id'=>174, 'contextlevel'=>50, 'instanceid'=>175);
|
||||
$this->assertEqual($sample, $cache->get(50, 175));
|
||||
$this->assertEqual($sample, $cache->get_by_id(174));
|
||||
|
||||
// Now add one more; should result in size being reduced
|
||||
$context = (object)array('id'=>99999, 'contextlevel'=>50,
|
||||
'instanceid'=>99999);
|
||||
$cache->add($context);
|
||||
$this->assertEqual(context_cache::MAX_SIZE - context_cache::REDUCE_SIZE + 1,
|
||||
$cache->get_approx_count());
|
||||
|
||||
// Check that the first ones are no longer there
|
||||
$this->assertEqual(false, $cache->get(50, 175));
|
||||
$this->assertEqual(false, $cache->get_by_id(174));
|
||||
|
||||
// Check that the last ones are still there
|
||||
$bigid = context_cache::MAX_SIZE - 10;
|
||||
$sample = (object)array(
|
||||
'id'=>$bigid, 'contextlevel'=>50, 'instanceid'=>$bigid+1);
|
||||
$this->assertEqual($sample, $cache->get(50, $bigid+1));
|
||||
$this->assertEqual($sample, $cache->get_by_id($bigid));
|
||||
|
||||
// Reset the cache
|
||||
$cache->reset();
|
||||
$this->assertEqual(0, $cache->get_approx_count());
|
||||
$this->assertEqual(false, $cache->get(50, $bigid+1));
|
||||
}
|
||||
}
|
||||
|
||||
+5
-5
@@ -1417,11 +1417,11 @@ function upgrade_core($version, $verbose) {
|
||||
purge_all_caches();
|
||||
|
||||
// Clean up contexts - more and more stuff depends on existence of paths and contexts
|
||||
cleanup_contexts();
|
||||
create_contexts();
|
||||
build_context_path();
|
||||
$syscontext = get_context_instance(CONTEXT_SYSTEM);
|
||||
mark_context_dirty($syscontext->path);
|
||||
context_helper::cleanup_instances();
|
||||
context_helper::create_instances(null, false);
|
||||
context_helper::build_all_paths(false);
|
||||
$syscontext = context_system::instance();
|
||||
$syscontext->mark_dirty();
|
||||
|
||||
print_upgrade_part_end('moodle', false, $verbose);
|
||||
} catch (Exception $ex) {
|
||||
|
||||
@@ -56,6 +56,9 @@ if (!empty($user)) {
|
||||
}
|
||||
}
|
||||
|
||||
// let enrol plugins deal with new enrolments if necessary
|
||||
enrol_check_plugins($user);
|
||||
|
||||
// setup user session to check capability
|
||||
session_set_user($user);
|
||||
|
||||
|
||||
+7
-3
@@ -16,9 +16,9 @@
|
||||
|
||||
/**
|
||||
* rss/file.php - entry point to serve rss streams
|
||||
*
|
||||
*
|
||||
* This script simply checks the parameters to construct a $USER
|
||||
* then finds and calls a function in the relevant component to
|
||||
* then finds and calls a function in the relevant component to
|
||||
* actually check security and create the RSS stream
|
||||
*
|
||||
* @package moodlecore
|
||||
@@ -81,7 +81,7 @@ if ($token==="$inttoken") {
|
||||
if (!isset($modinfo->instances[$componentname])) {
|
||||
$modinfo->instances[$componentname] = array();
|
||||
}
|
||||
|
||||
|
||||
foreach ($modinfo->instances[$componentname] as $modinstanceid=>$cm) {
|
||||
if ($modinstanceid==$instanceid) {
|
||||
$context = get_context_instance(CONTEXT_MODULE, $cm->id);
|
||||
@@ -122,6 +122,10 @@ if ($token==="$inttoken") {
|
||||
}
|
||||
|
||||
$user = get_complete_user_data('id', $userid);
|
||||
|
||||
// let enrol plugins deal with new enrolments if necessary
|
||||
enrol_check_plugins($user);
|
||||
|
||||
session_set_user($user); //for login and capability checks
|
||||
|
||||
// Check the context actually exists
|
||||
|
||||
@@ -654,6 +654,7 @@ abstract class webservice_server implements webservice_server_interface {
|
||||
}
|
||||
|
||||
// now fake user login, the session is completely empty too
|
||||
enrol_check_plugins($user);
|
||||
session_set_user($user);
|
||||
$this->userid = $user->id;
|
||||
|
||||
|
||||
@@ -66,6 +66,8 @@ $user = $DB->get_record('user', array('id'=>$token->userid, 'deleted'=>0), '*',
|
||||
// log token access
|
||||
$DB->set_field('external_tokens', 'lastaccess', time(), array('id'=>$token->id));
|
||||
|
||||
// let enrol plugins deal with new enrolments if necessary
|
||||
enrol_check_plugins($user);
|
||||
session_set_user($user);
|
||||
$context = get_context_instance(CONTEXT_USER, $USER->id);
|
||||
require_capability('moodle/user:manageownfiles', $context);
|
||||
|
||||
Reference in New Issue
Block a user