Exemplo n.º 1
0
/**
 * @param integer $quizid the id of the quiz object.
 * @return boolean Whether this quiz has any non-blank feedback text.
 */
function quiz_has_feedback($quizid)
{
    static $cache = array();
    if (!array_key_exists($quizid, $cache)) {
        $cache[$quizid] = record_exists_select('quiz_feedback', "quizid = {$quizid} AND " . sql_isnotempty('quiz_feedback', 'feedbacktext', false, true));
    }
    return $cache[$quizid];
}
Exemplo n.º 2
0
/**
 * Given one user object (from backup file), perform all the neccesary
 * checks is order to decide how that user will be handled on restore.
 *
 * Note the function requires $user->mnethostid to be already calculated
 * so it's caller responsibility to set it
 *
 * This function is used both by @restore_precheck_users() and
 * @restore_create_users() to get consistent results in both places
 *
 * It returns:
 *   - one user object (from DB), if match has been found and user will be remapped
 *   - boolean true if the user needs to be created
 *   - boolean false if some conflict happened and the user cannot be handled
 *
 * Each test is responsible for returning its results and interrupt
 * execution. At the end, boolean true (user needs to be created) will be
 * returned if no test has interrupted that.
 *
 * Here it's the logic applied, keep it updated:
 *
 *  If restoring users from same site backup:
 *      1A - Normal check: If match by id and username and mnethost  => ok, return target user
 *      1B - Handle users deleted in DB and "alive" in backup file:
 *           If match by id and mnethost and user is deleted in DB and
 *           (match by username LIKE 'backup_email.%' or by non empty email = md5(username)) => ok, return target user
 *      1C - Handle users deleted in backup file and "alive" in DB:
 *           If match by id and mnethost and user is deleted in backup file
 *           and match by email = email_without_time(backup_email) => ok, return target user
 *      1D - Conflict: If match by username and mnethost and doesn't match by id => conflict, return false
 *      1E - None of the above, return true => User needs to be created
 *
 *  if restoring from another site backup (cannot match by id here, replace it by email/firstaccess combination):
 *      2A - Normal check: If match by username and mnethost and (email or non-zero firstaccess) => ok, return target user
 *      2B - Handle users deleted in DB and "alive" in backup file:
 *           2B1 - If match by mnethost and user is deleted in DB and not empty email = md5(username) and
 *                 (username LIKE 'backup_email.%' or non-zero firstaccess) => ok, return target user
 *           2B2 - If match by mnethost and user is deleted in DB and
 *                 username LIKE 'backup_email.%' and non-zero firstaccess) => ok, return target user
 *                 (to cover situations were md5(username) wasn't implemented on delete we requiere both)
 *      2C - Handle users deleted in backup file and "alive" in DB:
 *           If match mnethost and user is deleted in backup file
 *           and by email = email_without_time(backup_email) and non-zero firstaccess=> ok, return target user
 *      2D - Conflict: If match by username and mnethost and not by (email or non-zero firstaccess) => conflict, return false
 *      2E - None of the above, return true => User needs to be created
 *
 * Note: for DB deleted users email is stored in username field, hence we
 *       are looking there for emails. See delete_user()
 * Note: for DB deleted users md5(username) is stored *sometimes* in the email field,
 *       hence we are looking there for usernames if not empty. See delete_user()
 */
function restore_check_user($restore, $user)
{
    global $CFG;
    // Verify mnethostid is set, return error if not
    // it's parent responsibility to define that before
    // arriving here
    if (empty($user->mnethostid)) {
        debugging("restore_check_user() wrong use, mnethostid not set for user {$user->username}", DEBUG_DEVELOPER);
        return false;
    }
    // Handle checks from same site backups
    if (backup_is_same_site($restore) && empty($CFG->forcedifferentsitecheckingusersonrestore)) {
        // 1A - If match by id and username and mnethost => ok, return target user
        if ($rec = get_record('user', 'id', $user->id, 'username', addslashes($user->username), 'mnethostid', $user->mnethostid)) {
            return $rec;
            // Matching user found, return it
        }
        // 1B - Handle users deleted in DB and "alive" in backup file
        // Note: for DB deleted users email is stored in username field, hence we
        //       are looking there for emails. See delete_user()
        // Note: for DB deleted users md5(username) is stored *sometimes* in the email field,
        //       hence we are looking there for usernames if not empty. See delete_user()
        // If match by id and mnethost and user is deleted in DB and
        // match by username LIKE 'backup_email.%' or by non empty email = md5(username) => ok, return target user
        if ($rec = get_record_sql("SELECT *\n                                         FROM {$CFG->prefix}user u\n                                        WHERE id = {$user->id}\n                                          AND mnethostid = {$user->mnethostid}\n                                          AND deleted = 1\n                                          AND (\n                                                  username LIKE '" . addslashes($user->email) . ".%'\n                                               OR (\n                                                      " . sql_isnotempty('user', 'email', false, false) . "\n                                                  AND email = '" . md5($user->username) . "'\n                                                  )\n                                              )")) {
            return $rec;
            // Matching user, deleted in DB found, return it
        }
        // 1C - Handle users deleted in backup file and "alive" in DB
        // If match by id and mnethost and user is deleted in backup file
        // and match by email = email_without_time(backup_email) => ok, return target user
        if ($user->deleted) {
            // Note: for DB deleted users email is stored in username field, hence we
            //       are looking there for emails. See delete_user()
            // Trim time() from email
            $trimemail = preg_replace('/(.*?)\\.[0-9]+.?$/', '\\1', $user->username);
            if ($rec = get_record_sql("SELECT *\n                                             FROM {$CFG->prefix}user u\n                                            WHERE id = {$user->id}\n                                              AND mnethostid = {$user->mnethostid}\n                                              AND email = '" . addslashes($trimemail) . "'")) {
                return $rec;
                // Matching user, deleted in backup file found, return it
            }
        }
        // 1D - If match by username and mnethost and doesn't match by id => conflict, return false
        if ($rec = get_record('user', 'username', addslashes($user->username), 'mnethostid', $user->mnethostid)) {
            if ($user->id != $rec->id) {
                return false;
                // Conflict, username already exists and belongs to another id
            }
        }
        // Handle checks from different site backups
    } else {
        // 2A - If match by username and mnethost and
        //     (email or non-zero firstaccess) => ok, return target user
        if ($rec = get_record_sql("SELECT *\n                                         FROM {$CFG->prefix}user u\n                                        WHERE username = '******'\n                                          AND mnethostid = {$user->mnethostid}\n                                          AND (\n                                                  email = '" . addslashes($user->email) . "'\n                                               OR (\n                                                      firstaccess != 0\n                                                  AND firstaccess = {$user->firstaccess}\n                                                  )\n                                              )")) {
            return $rec;
            // Matching user found, return it
        }
        // 2B - Handle users deleted in DB and "alive" in backup file
        // Note: for DB deleted users email is stored in username field, hence we
        //       are looking there for emails. See delete_user()
        // Note: for DB deleted users md5(username) is stored *sometimes* in the email field,
        //       hence we are looking there for usernames if not empty. See delete_user()
        // 2B1 - If match by mnethost and user is deleted in DB and not empty email = md5(username) and
        //       (by username LIKE 'backup_email.%' or non-zero firstaccess) => ok, return target user
        if ($rec = get_record_sql("SELECT *\n                                         FROM {$CFG->prefix}user u\n                                        WHERE mnethostid = {$user->mnethostid}\n                                          AND deleted = 1\n                                          AND " . sql_isnotempty('user', 'email', false, false) . "\n                                          AND email = '" . md5($user->username) . "'\n                                          AND (\n                                                  username LIKE '" . addslashes($user->email) . ".%'\n                                               OR (\n                                                      firstaccess != 0\n                                                  AND firstaccess = {$user->firstaccess}\n                                                  )\n                                              )")) {
            return $rec;
            // Matching user found, return it
        }
        // 2B2 - If match by mnethost and user is deleted in DB and
        //       username LIKE 'backup_email.%' and non-zero firstaccess) => ok, return target user
        //       (this covers situations where md5(username) wasn't being stored so we require both
        //        the email & non-zero firstaccess to match)
        if ($rec = get_record_sql("SELECT *\n                                         FROM {$CFG->prefix}user u\n                                        WHERE mnethostid = {$user->mnethostid}\n                                          AND deleted = 1\n                                          AND username LIKE '" . addslashes($user->email) . ".%'\n                                          AND firstaccess != 0\n                                          AND firstaccess = {$user->firstaccess}")) {
            return $rec;
            // Matching user found, return it
        }
        // 2C - Handle users deleted in backup file and "alive" in DB
        // If match mnethost and user is deleted in backup file
        // and match by email = email_without_time(backup_email) and non-zero firstaccess=> ok, return target user
        if ($user->deleted) {
            // Note: for DB deleted users email is stored in username field, hence we
            //       are looking there for emails. See delete_user()
            // Trim time() from email
            $trimemail = preg_replace('/(.*?)\\.[0-9]+.?$/', '\\1', $user->username);
            if ($rec = get_record_sql("SELECT *\n                                             FROM {$CFG->prefix}user u\n                                            WHERE mnethostid = {$user->mnethostid}\n                                              AND email = '" . addslashes($trimemail) . "'\n                                              AND firstaccess != 0\n                                              AND firstaccess = {$user->firstaccess}")) {
                return $rec;
                // Matching user, deleted in backup file found, return it
            }
        }
        // 2D - If match by username and mnethost and not by (email or non-zero firstaccess) => conflict, return false
        if ($rec = get_record_sql("SELECT *\n                                         FROM {$CFG->prefix}user u\n                                        WHERE username = '******'\n                                          AND mnethostid = {$user->mnethostid}\n                                      AND NOT (\n                                                  email = '" . addslashes($user->email) . "'\n                                               OR (\n                                                      firstaccess != 0\n                                                  AND firstaccess = {$user->firstaccess}\n                                                  )\n                                              )")) {
            return false;
            // Conflict, username/mnethostid already exist and belong to another user (by email/firstaccess)
        }
    }
    // Arrived here, return true as the user will need to be created and no
    // conflicts have been found in the logic above. This covers:
    // 1E - else => user needs to be created, return true
    // 2E - else => user needs to be created, return true
    return true;
}