$modlurals = array();
- $cmids = array();
- $contexts = null;
- foreach ($info as $mod) {
- $cmids[$mod->cm] = $mod->cm;
- }
- if ($cmids) {
- // preload all module contexts with one query
- $contexts = get_context_instance(CONTEXT_MODULE, $cmids);
- }
+ // If we haven't already preloaded contexts for the course, do it now
+ preload_course_contexts($course->id);
foreach ($info as $mod) {
if (empty($mod->name)) {
$modlurals[$cm->modname] = get_string('modulenameplural', $cm->modname);
}
$cm->modplural = $modlurals[$cm->modname];
-
+ $modcontext = get_context_instance(CONTEXT_MODULE,$cm->id);
+
if(!empty($CFG->enableavailability)) {
// Unfortunately the next call really wants to call
// get_fast_modinfo, but that would be recursive, so we fake up a
} else {
$cm->available=true;
}
- if ((!$cm->visible or !$cm->available) and !has_capability('moodle/course:viewhiddenactivities', $contexts[$cm->id], $userid)) {
+ if ((!$cm->visible or !$cm->available) and !has_capability('moodle/course:viewhiddenactivities', $modcontext, $userid)) {
$cm->uservisible = false;
} else if (!empty($CFG->enablegroupings) and !empty($cm->groupmembersonly)
- and !has_capability('moodle/site:accessallgroups', $contexts[$cm->id], $userid)) {
+ and !has_capability('moodle/site:accessallgroups', $modcontext, $userid)) {
if (is_null($modinfo->groups)) {
$modinfo->groups = groups_get_user_groups($course->id, $userid);
}
return true;
}
+/**
+ * Preloads all contexts relating to a course: course, modules, and blocks.
+ *
+ * @param int $courseid Course ID
+ */
+function preload_course_contexts($courseid) {
+ global $context_cache, $context_cache_id, $CFG, $DB;
+
+ // Users can call this multiple times without doing any harm
+ static $preloadedcourses=array();
+ if(array_key_exists($courseid,$preloadedcourses)) {
+ return;
+ }
+
+ $rs=$DB->get_recordset_sql("
+SELECT
+ x.instanceid, x.id, x.contextlevel, x.path, x.depth
+FROM
+ {course_modules} cm
+ INNER JOIN {context} x ON x.instanceid=cm.id
+WHERE
+ cm.course=?
+ AND x.contextlevel=".CONTEXT_MODULE."
+UNION ALL
+SELECT
+ x.instanceid, x.id, x.contextlevel, x.path, x.depth
+FROM
+ {block_instance} bi
+ INNER JOIN {context} x ON x.instanceid=bi.id
+WHERE
+ bi.pageid=?
+ AND bi.pagetype='course-view'
+ AND x.contextlevel=".CONTEXT_BLOCK."
+UNION ALL
+SELECT
+ x.instanceid, x.id, x.contextlevel, x.path, x.depth
+FROM
+ {context} x
+WHERE
+ x.instanceid=?
+ AND x.contextlevel=".CONTEXT_COURSE."
+",array($courseid,$courseid,$courseid)); // Note, repetition of parameter annoying but required
+ foreach($rs as $context) {
+ $context_cache[$context->contextlevel][$context->instanceid] = $context;
+ $context_cache_id[$context->id] = $context;
+ }
+ $rs->close();
+ $preloadedcourses[$courseid]=true;
+}
+
/**
* Get the context instance as an object. This function will create the
* context instance if it does not exist yet.