MDL-46682 auth/db: Increase of chunk size and update change.

The update query was not checking the mnet auth id and could
have been updating the wrong entry.
This commit is contained in:
Adrian Greeve 2016-07-06 09:48:37 +08:00
parent 6f08f36c49
commit 3261b9eeea

View file

@ -303,19 +303,19 @@ class auth_plugin_db extends auth_plugin_base {
// Find obsolete users. // Find obsolete users.
if (count($userlist)) { if (count($userlist)) {
$remove_users = array(); $remove_users = array();
// Oracle IN clause is limited to 1000 parameters. We need to chunk the SQL. // All the drivers can cope with chunks of 10,000. See line 4491 of lib/dml/tests/dml_est.php
$userlistchunks = array_chunk($userlist , 999); $userlistchunks = array_chunk($userlist , 10000);
foreach($userlistchunks as $userlistchunk) { foreach($userlistchunks as $userlistchunk) {
list($notin_sql, $params) = $DB->get_in_or_equal($userlistchunk, SQL_PARAMS_NAMED, 'u', false); list($notin_sql, $params) = $DB->get_in_or_equal($userlistchunk, SQL_PARAMS_NAMED, 'u', false);
$params['authtype'] = $this->authtype; $params['authtype'] = $this->authtype;
$sql = "SELECT u.* $sql = "SELECT u.id, u.username
FROM {user} u FROM {user} u
WHERE u.auth=:authtype AND u.deleted=0 AND u.mnethostid=:mnethostid $suspendselect AND u.username $notin_sql"; WHERE u.auth=:authtype AND u.deleted=0 AND u.mnethostid=:mnethostid $suspendselect AND u.username $notin_sql";
$params['mnethostid'] = $CFG->mnet_localhost_id; $params['mnethostid'] = $CFG->mnet_localhost_id;
$remove_users = $remove_users + $DB->get_records_sql($sql, $params); $remove_users = $remove_users + $DB->get_records_sql($sql, $params);
} }
} else { } else {
$sql = "SELECT u.* $sql = "SELECT u.id, u.username
FROM {user} u FROM {user} u
WHERE u.auth=:authtype AND u.deleted=0 AND u.mnethostid=:mnethostid $suspendselect"; WHERE u.auth=:authtype AND u.deleted=0 AND u.mnethostid=:mnethostid $suspendselect";
$params = array(); $params = array();
@ -366,14 +366,15 @@ class auth_plugin_db extends auth_plugin_base {
// Only go ahead if we actually have fields to update locally. // Only go ahead if we actually have fields to update locally.
if (!empty($updatekeys)) { if (!empty($updatekeys)) {
$update_users = array(); $update_users = array();
// Oracle IN clause is limited to 1000 parameters. We need to chunk the SQL. // All the drivers can cope with chunks of 10,000. See line 4491 of lib/dml/tests/dml_est.php
$userlistchunks = array_chunk($userlist , 999); $userlistchunks = array_chunk($userlist , 10000);
foreach($userlistchunks as $userlistchunk) { foreach($userlistchunks as $userlistchunk) {
list($in_sql, $params) = $DB->get_in_or_equal($userlistchunk, SQL_PARAMS_NAMED, 'u', true); list($in_sql, $params) = $DB->get_in_or_equal($userlistchunk, SQL_PARAMS_NAMED, 'u', true);
$params['authtype'] = $this->authtype; $params['authtype'] = $this->authtype;
$params['mnethostid'] = $CFG->mnet_localhost_id;
$sql = "SELECT u.id, u.username $sql = "SELECT u.id, u.username
FROM {user} u FROM {user} u
WHERE u.auth=:authtype AND u.deleted=0 AND u.username {$in_sql}"; WHERE u.auth = :authtype AND u.deleted = 0 AND u.mnethostid = :mnethostid AND u.username {$in_sql}";
$update_users = $update_users + $DB->get_records_sql($sql, $params); $update_users = $update_users + $DB->get_records_sql($sql, $params);
} }