Moodle Plugins directory: Cohort members to group | Moodle.org
Cohort members to group
Enrolment ::: enrol_groupsync
Maintained by
Jorge C.
Cohort to group sync for users already enrolled via different method.
Latest release:
962 sites
175 downloads
55 fans
This Moodle enrolment plugin synchronises cohort and group memberships. It does not make any user enrolments. Only users that are enrolled via other enrolment method are automatically put into groups based on their cohort membership.
Contributors
Jorge C. (Lead maintainer)
Petr Skoda: Original author
David Mudrák: Legacy maintainer
Amaia Anabitarte
Please login to view contributors details and/or to contact them
Hi Chye Siaw. The plugin makes use of observing events that trigger when the user is enrolled to the course or added to a cohort.
That's weird that the CLI script did not work for you. Have you tried to run it in the verbose mode?
Hi Robert. There is no UI for that. I suppose that Chye made some low-level operations directly in the
enroltable, which is something I'd generallyt discourage from doing so, unless you know what you're doing.Hi Learning Works. Sorry, I have no idea what you are referring to? That field is part of the self enrolment form AFAIK. This plugin does not touch any enrolment at all.
According to https://moodle.org/plugins/enrol_groupsync/stats there are some 4.2 sites having the plugins installed. It still needs to be tested on new PHP versions. Any help and feedback will be welcome.
When we call the webservice core_cohort_delete_cohort_members the service calls an event:
[
'eventname' => '\core\event\cohort_member_removed',
'callback' => 'enrol_groupsync_observer::cohort_member_removed',
],
The enrol_groupsync listens to that event and runs the following code:
public static function cohort_member_removed(\core\event\cohort_member_removed $event) {
global $DB, $CFG;
require_once($CFG->dirroot.'/group/lib.php');
if (!enrol_is_enabled('groupsync')) {
return true;
}
$sql = "SELECT DISTINCT e.id, e.customint2
FROM {enrol} e
JOIN {groups} g ON (g.id = e.customint2 AND g.courseid = e.courseid)
JOIN {groups_members} gm ON (gm.userid = :userid AND gm.groupid = g.id AND gm.component = 'enrol_groupsync'
AND gm.itemid = e.id)
WHERE e.customint1 = :cohortid AND e.enrol = 'groupsync'
ORDER BY e.id ASC";
$instances = $DB->get_records_sql($sql, ['cohortid' => $event->objectid, 'userid' => $event->relateduserid]);
foreach ($instances as $instance) {
groups_remove_member($instance->customint2, $event->relateduserid);
}
return true;
}
Which fails:
#0 /var/www/html/moodle/lib/dml/moodle_transaction.php(105): moodle_database->rollback_delegated_transaction(Object(moodle_transaction), Object(moodle_exception))
#1 /var/www/html/moodle/lib/grade/grade_grade.php(1160): moodle_transaction->rollback(Object(moodle_exception))
#2 /var/www/html/moodle/lib/gradelib.php(1577): grade_grade->delete('...')
#3 /var/www/html/moodle/lib/enrollib.php(2338): grade_user_unenrol('...', '...')
#4 /var/www/html/moodle/enrol/cohort/locallib.php(110): enrol_plugin->unenrol_user(Object(stdClass), '...')
#5 [internal function]: enrol_cohort_handler::member_removed(Object(core\event\cohort_member_removed))
#6 /var/www/html/moodle/lib/classes/event/manager.php(155): call_user_func('...', Object(core\event\cohort_member_removed))
#7 /var/www/html/moodle/lib/classes/event/manager.php(75): core\event\manager::process_buffers()
#8 /var/www/html/moodle/lib/classes/event/base.php(795): core\event\manager::dispatch(Object(core\event\cohort_member_removed))
#9 /var/www/html/moodle/cohort/lib.php(230): core\event\base->trigger()
#10 /var/www/html/moodle/cohort/externallib.php(789): cohort_remove_member('...', '...')
#11 /var/www/html/moodle/webservice/lib.php(1504): core_cohort_external::delete_cohort_members(Array)
#12 /var/www/html/moodle/webservice/lib.php(1350): webservice_base_server->execute()
#13 /var/www/html/moodle/webservice/rest/server.php(44): webservice_base_server->run()
As you see in line two it has something to do with deleting grades. It only happens to some users in some cohorts and if you unenrol them through Moodle, it doesn't fail and afterwards you are again able to call the webservice with no errors.
We are using Moodle 4.4.10 (to be upgraded 6 Jan. 2026 to Moodle 5.0.3)
Is this something you could have a look at.
Kind regards,
Ulrik McArdle, Moxis
Premium partner
I've tested the plugin on Moodle 4.4.10 and have not been able to reproduce the error. The stack trace indicates that the failure occurs within Moodle core’s grade deletion process, specifically in the sequence enrol_cohort → grade_user_unenrol() → grade_grade->delete() and is unrelated to the enrol_groupsync observer. The groupsync handler only removes the user from synced groups after the cohort removal event triggers, without affecting the grade record deletion path. Note that enrol_cohort plugin also has its own observer for the cohort_member_removed event, which is the one referenced in frame #4.
Let me know if I can assist with further debugging or tracing.