Skip to content

Commit

Permalink
MDL-17929 enrol: Populate groups from Child Courses in META courses
Browse files Browse the repository at this point in the history
This is based on code from the enrol cohort plugin and
on work from Willy Lee available at https://github.com/willylee/moodle-local_metasync

AMOS BEGIN
  CPY [addgroup,enrol_cohort],[addgroup,enrol_meta]
AMOS END
  • Loading branch information
danielneis authored and marinaglancy committed Apr 22, 2015
1 parent df9981c commit 98177a4
Show file tree
Hide file tree
Showing 5 changed files with 96 additions and 4 deletions.
3 changes: 2 additions & 1 deletion enrol/meta/addinstance.php
Expand Up @@ -51,7 +51,8 @@
redirect(new moodle_url('/enrol/instances.php', array('id'=>$course->id)));

} else if ($data = $mform->get_data()) {
$eid = $enrol->add_instance($course, array('customint1'=>$data->link));
$eid = $enrol->add_instance($course, array('customint1' => $data->link,
'customint2' => $data->customint2));
enrol_meta_sync($course->id);
if (!empty($data->submitbuttonnext)) {
redirect(new moodle_url('/enrol/meta/addinstance.php',
Expand Down
7 changes: 7 additions & 0 deletions enrol/meta/addinstance_form.php
Expand Up @@ -64,11 +64,18 @@ function definition() {
}
$rs->close();

$groups = array(0 => get_string('none'));
foreach (groups_get_all_groups($course->id) as $group) {
$groups[$group->id] = format_string($group->name, true, array('context' => course_context::instance($course->id)));
}

$mform->addElement('header','general', get_string('pluginname', 'enrol_meta'));

$mform->addElement('select', 'link', get_string('linkedcourse', 'enrol_meta'), $courses);
$mform->addRule('link', get_string('required'), 'required', null, 'client');

$mform->addElement('select', 'customint2', get_string('addgroup', 'enrol_meta'), $groups);

$mform->addElement('hidden', 'id', null);
$mform->setType('id', PARAM_INT);

Expand Down
3 changes: 2 additions & 1 deletion enrol/meta/lang/en/enrol_meta.php
Expand Up @@ -22,6 +22,7 @@
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/

$string['addgroup'] = 'Add to group';
$string['coursesort'] = 'Sort course list';
$string['coursesort_help'] = 'This determines whether the list of courses that can be linked are sorted by sort order (i.e. the order set in Site administration > Courses > Manage courses and categories) or alphabetically by course setting.';
$string['linkedcourse'] = 'Link course';
Expand All @@ -33,4 +34,4 @@
$string['pluginname'] = 'Course meta link';
$string['pluginname_desc'] = 'Course meta link enrolment plugin synchronises enrolments and roles in two different courses.';
$string['syncall'] = 'Synchronise all enrolled users';
$string['syncall_desc'] = 'If enabled all enrolled users are synchronised even if they have no role in parent course, if disabled only users that have at least one synchronised role are enrolled in child course.';
$string['syncall_desc'] = 'If enabled all enrolled users are synchronised even if they have no role in parent course, if disabled only users that have at least one synchronised role are enrolled in child course.';
46 changes: 46 additions & 0 deletions enrol/meta/locallib.php
Expand Up @@ -150,18 +150,21 @@ protected static function sync_with_parent_course(stdClass $instance, $userid) {
}
}


// enrol user if not enrolled yet or fix status
if ($ue) {
if ($parentstatus != $ue->status) {
$plugin->update_user_enrol($instance, $userid, $parentstatus);
$ue->status = $parentstatus;
groups_add_member($instance->customint2, $userid, 'enrol_meta', $instance->courseid);
}
} else {
$plugin->enrol_user($instance, $userid, NULL, 0, 0, $parentstatus);
$ue = new stdClass();
$ue->userid = $userid;
$ue->enrolid = $instance->id;
$ue->status = $parentstatus;
groups_add_member($instance->customint2, $userid, 'enrol_meta', $instance->courseid);
}

$unenrolaction = $plugin->get_config('unenrolaction', ENROL_EXT_REMOVED_SUSPENDNOROLES);
Expand All @@ -171,6 +174,7 @@ protected static function sync_with_parent_course(stdClass $instance, $userid) {
if ($unenrolaction == ENROL_EXT_REMOVED_SUSPEND) {
// Always keep the roles.
} else if ($roles) {
groups_remove_member($instance->customint2, $userid);
role_unassign_all(array('userid'=>$userid, 'contextid'=>$context->id, 'component'=>'enrol_meta', 'itemid'=>$instance->id));
}
return;
Expand All @@ -180,6 +184,7 @@ protected static function sync_with_parent_course(stdClass $instance, $userid) {
foreach ($parentroles as $rid) {
if (!isset($roles[$rid])) {
role_assign($rid, $userid, $context->id, 'enrol_meta', $instance->id);
groups_add_member($instance->customint2, $userid, 'enrol_meta', $instance->courseid);
}
}

Expand Down Expand Up @@ -227,6 +232,8 @@ protected static function user_not_supposed_to_be_here($instance, $ue, context_c
if ($ue->status != ENROL_USER_SUSPENDED) {
$plugin->update_user_enrol($instance, $userid, ENROL_USER_SUSPENDED);
}
// Remove from metagroup.
groups_remove_member($instance->customint2, $userid);
role_unassign_all(array('userid'=>$userid, 'contextid'=>$context->id, 'component'=>'enrol_meta', 'itemid'=>$instance->id));

} else {
Expand All @@ -244,6 +251,7 @@ protected static function user_not_supposed_to_be_here($instance, $ue, context_c
*/
function enrol_meta_sync($courseid = NULL, $verbose = false) {
global $CFG, $DB;
require_once("{$CFG->dirroot}/group/lib.php");

// purge all roles if meta sync disabled, those can be recreated later here in cron
if (!enrol_is_enabled('meta')) {
Expand Down Expand Up @@ -544,6 +552,44 @@ function enrol_meta_sync($courseid = NULL, $verbose = false) {
}
}

// Finally sync groups.
$onecourse = $courseid ? "AND e.courseid = :courseid" : "";

// Remove invalid.
$sql = "SELECT gm.*, e.courseid, g.name AS groupname
FROM {groups_members} gm
JOIN {groups} g ON (g.id = gm.groupid)
JOIN {enrol} e ON (e.enrol = 'meta' AND e.courseid = g.courseid $onecourse)
JOIN {user_enrolments} ue ON (ue.userid = gm.userid AND ue.enrolid = e.id)
WHERE gm.component='enrol_meta' AND gm.itemid = e.id AND g.id <> e.customint2";
$params = array();
$params['courseid'] = $courseid;

$rs = $DB->get_recordset_sql($sql, $params);
foreach ($rs as $gm) {
groups_remove_member($gm->groupid, $gm->userid);
mtrace("removing user from group: $gm->userid ==> $gm->courseid - $gm->groupname", 1);
}
$rs->close();

// Add missing.
$sql = "SELECT ue.*, g.id AS groupid, e.courseid, g.name AS groupname
FROM {user_enrolments} ue
JOIN {enrol} e ON (e.id = ue.enrolid AND e.enrol = 'meta' $onecourse)
JOIN {groups} g ON (g.courseid = e.courseid AND g.id = e.customint2)
JOIN {user} u ON (u.id = ue.userid AND u.deleted = 0)
LEFT JOIN {groups_members} gm ON (gm.groupid = g.id AND gm.userid = ue.userid)
WHERE gm.id IS NULL";
$params = array();
$params['courseid'] = $courseid;

$rs = $DB->get_recordset_sql($sql, $params);
foreach ($rs as $ue) {
groups_add_member($ue->groupid, $ue->userid, 'enrol_meta', $ue->enrolid);
mtrace("adding user to group: $ue->userid ==> $ue->courseid - $ue->groupname", 1);
}
$rs->close();

if ($verbose) {
mtrace('...user enrolment synchronisation finished.');
}
Expand Down
41 changes: 39 additions & 2 deletions enrol/meta/tests/plugin_test.php
Expand Up @@ -100,6 +100,13 @@ public function test_sync() {
$teacher = $DB->get_record('role', array('shortname'=>'teacher'));
$manager = $DB->get_record('role', array('shortname'=>'manager'));

$id = groups_create_group((object)array('name'=>'Group 1', 'courseid'=>$course1->id));
$group1 = $DB->get_record('groups', array('id'=>$id), '*', MUST_EXIST);
$id = groups_create_group((object)array('name'=>'Group 2', 'courseid'=>$course1->id));
$group2 = $DB->get_record('groups', array('id'=>$id), '*', MUST_EXIST);
$id = groups_create_group((object)array('name'=>'Group 3', 'courseid'=>$course2->id));
$group3 = $DB->get_record('groups', array('id'=>$id), '*', MUST_EXIST);

$this->disable_plugin();

$this->getDataGenerator()->enrol_user($user1->id, $course1->id, $student->id);
Expand Down Expand Up @@ -128,12 +135,14 @@ public function test_sync() {
$this->assertEquals(7, $DB->count_records('user_enrolments'));
$this->assertEquals(6, $DB->count_records('role_assignments'));

$e1 = $metalplugin->add_instance($course3, array('customint1'=>$course1->id));
$e2 = $metalplugin->add_instance($course3, array('customint1'=>$course2->id));
$e1 = $metalplugin->add_instance($course3, array('customint1'=>$course1->id, 'customint2'=>$group1->id));
$e2 = $metalplugin->add_instance($course3, array('customint1'=>$course2->id, 'customint2'=>$group2->id));
$e3 = $metalplugin->add_instance($course4, array('customint1'=>$course2->id));
$e4 = $metalplugin->add_instance($course4, array('customint1'=>$course2->id, 'customint2'=>$group3->id));
$enrol1 = $DB->get_record('enrol', array('id'=>$e1));
$enrol2 = $DB->get_record('enrol', array('id'=>$e2));
$enrol3 = $DB->get_record('enrol', array('id'=>$e3));
$enrol4 = $DB->get_record('enrol', array('id'=>$e3));

enrol_meta_sync($course4->id, false);
$this->assertEquals(9, $DB->count_records('user_enrolments'));
Expand Down Expand Up @@ -176,6 +185,34 @@ public function test_sync() {

$this->enable_plugin();

$this->assertTrue(is_enrolled(context_course::instance($course1->id), $user4));
$this->assertTrue(groups_add_member($group1, $user4));
$this->assertTrue(groups_add_member($group2, $user4));

$this->assertFalse(groups_is_member($group1->id, $user1->id));
groups_add_member($group1->id, $user1->id);
$this->assertTrue(groups_is_member($group1->id, $user1->id));
$this->assertTrue($DB->record_exists('groups_members', array('groupid'=>$group1->id, 'userid'=>$user1->id, 'component'=>'enrol_cohort', 'itemid'=>$cohortinstance1->id)));

groups_add_member($group1->id, $user4->id);
$this->assertTrue(groups_is_member($group1->id, $user4->id));
$this->assertFalse($DB->record_exists('groups_members', array('groupid'=>$group1->id, 'userid'=>$user4->id, 'component'=>'enrol_cohort', 'itemid'=>$cohortinstance1->id)));

set_config('unenrolaction', ENROL_EXT_REMOVED_UNENROL, 'enrol_meta');

groups_remove_member($group1->id, $user1->id);
$this->assertFalse(groups_is_member($group1->id, $user1->id));

groups_remove_member($group1->id, $user4->id);
$this->assertTrue(groups_is_member($group1->id, $user4->id));
$this->assertTrue(groups_is_member($group2->id, $user4->id));

set_config('unenrolaction', ENROL_EXT_REMOVED_SUSPENDNOROLES, 'enrol_meta');
groups_add_member($group1->id, $user1->id);

groups_remove_member($group1->id, $user1->id);
$this->assertTrue(groups_is_member($group1->id, $user1->id));

set_config('unenrolaction', ENROL_EXT_REMOVED_SUSPEND, 'enrol_meta');
enrol_meta_sync($course4->id, false);
$this->assertEquals(14, $DB->count_records('user_enrolments'));
Expand Down

0 comments on commit 98177a4

Please sign in to comment.