public function test_set_user() { global $USER, $DB; $this->assertEquals(0, $USER->id); $this->assertSame($_SESSION['USER'], $USER); $user = $DB->get_record('user', array('id' => 2)); $this->assertNotEmpty($user); $this->setUser($user); $this->assertEquals(2, $USER->id); $this->assertEquals(2, $_SESSION['USER']->id); $this->assertSame($_SESSION['USER'], $USER); $USER->id = 3; $this->assertEquals(3, $USER->id); $this->assertEquals(3, $_SESSION['USER']->id); $this->assertSame($_SESSION['USER'], $USER); session_set_user($user); $this->assertEquals(2, $USER->id); $this->assertEquals(2, $_SESSION['USER']->id); $this->assertSame($_SESSION['USER'], $USER); $USER = $DB->get_record('user', array('id' => 1)); $this->assertNotEmpty($USER); $this->assertEquals(1, $USER->id); $this->assertEquals(1, $_SESSION['USER']->id); $this->assertSame($_SESSION['USER'], $USER); $this->setUser(null); $this->assertEquals(0, $USER->id); $this->assertSame($_SESSION['USER'], $USER); }
public function __fav_user_login($user) { global $CFG, $USER; // regenerate session id and delete old session, // this helps prevent session fixation attacks from the same domain session_regenerate_id(true); // let enrol plugins deal with new enrolments if necessary enrol_check_plugins($user); // check enrolments, load caps and setup $USER object session_set_user($user); // reload preferences from DB unset($USER->preference); check_user_preferences_loaded($USER); // update login times update_user_login_times(); // extra session prefs init set_login_session_preferences(); if (isguestuser()) { // no need to continue when user is THE guest return $USER; } return $USER; }
/** * Authenticate user using username+password or token. * This function sets up $USER global. * It is safe to use has_capability() after this. * This method also verifies user is allowed to use this * server. * @return void */ protected function authenticate_user() { global $CFG, $DB; if (!NO_MOODLE_COOKIES) { throw new coding_exception('Cookies must be disabled in WS servers!'); } if ($this->authmethod == WEBSERVICE_AUTHMETHOD_USERNAME) { //we check that authentication plugin is enabled //it is only required by simple authentication if (!is_enabled_auth('webservice')) { throw new webservice_access_exception(get_string('wsauthnotenabled', 'webservice')); } if (!($auth = get_auth_plugin('webservice'))) { throw new webservice_access_exception(get_string('wsauthmissing', 'webservice')); } $this->restricted_context = get_context_instance(CONTEXT_SYSTEM); if (!$this->username) { throw new webservice_access_exception(get_string('missingusername', 'webservice')); } if (!$this->password) { throw new webservice_access_exception(get_string('missingpassword', 'webservice')); } if (!$auth->user_login_webservice($this->username, $this->password)) { // log failed login attempts add_to_log(SITEID, 'webservice', get_string('simpleauthlog', 'webservice'), '', get_string('failedtolog', 'webservice') . ": " . $this->username . "/" . $this->password . " - " . getremoteaddr(), 0); throw new webservice_access_exception(get_string('wrongusernamepassword', 'webservice')); } $user = $DB->get_record('user', array('username' => $this->username, 'mnethostid' => $CFG->mnet_localhost_id, 'deleted' => 0), '*', MUST_EXIST); } else { if ($this->authmethod == WEBSERVICE_AUTHMETHOD_PERMANENT_TOKEN) { $user = $this->authenticate_by_token(EXTERNAL_TOKEN_PERMANENT); } else { $user = $this->authenticate_by_token(EXTERNAL_TOKEN_EMBEDDED); } } // now fake user login, the session is completely empty too session_set_user($user); $this->userid = $user->id; if ($this->authmethod != WEBSERVICE_AUTHMETHOD_SESSION_TOKEN && !has_capability("webservice/{$this->wsname}:use", $this->restricted_context)) { throw new webservice_access_exception(get_string('accessnotallowed', 'webservice')); } external_api::set_context_restriction($this->restricted_context); }
/** * Authenticate user using username+password or token. * This function sets up $USER global. * It is safe to use has_capability() after this. * This method also verifies user is allowed to use this * server. */ protected function authenticate_user() { global $CFG, $DB; if (!NO_MOODLE_COOKIES) { throw new coding_exception('Cookies must be disabled in WS servers!'); } if ($this->authmethod == WEBSERVICE_AUTHMETHOD_USERNAME) { //we check that authentication plugin is enabled //it is only required by simple authentication if (!is_enabled_auth('webservice')) { throw new webservice_access_exception(get_string('wsauthnotenabled', 'webservice')); } if (!($auth = get_auth_plugin('webservice'))) { throw new webservice_access_exception(get_string('wsauthmissing', 'webservice')); } $this->restricted_context = get_context_instance(CONTEXT_SYSTEM); if (!$this->username) { throw new webservice_access_exception(get_string('missingusername', 'webservice')); } if (!$this->password) { throw new webservice_access_exception(get_string('missingpassword', 'webservice')); } if (!$auth->user_login_webservice($this->username, $this->password)) { // log failed login attempts add_to_log(SITEID, 'webservice', get_string('simpleauthlog', 'webservice'), '', get_string('failedtolog', 'webservice') . ": " . $this->username . "/" . $this->password . " - " . getremoteaddr(), 0); throw new webservice_access_exception(get_string('wrongusernamepassword', 'webservice')); } $user = $DB->get_record('user', array('username' => $this->username, 'mnethostid' => $CFG->mnet_localhost_id), '*', MUST_EXIST); } else { if ($this->authmethod == WEBSERVICE_AUTHMETHOD_PERMANENT_TOKEN) { $user = $this->authenticate_by_token(EXTERNAL_TOKEN_PERMANENT); } else { $user = $this->authenticate_by_token(EXTERNAL_TOKEN_EMBEDDED); } } //Non admin can not authenticate if maintenance mode $hassiteconfig = has_capability('moodle/site:config', get_context_instance(CONTEXT_SYSTEM), $user); if (!empty($CFG->maintenance_enabled) and !$hassiteconfig) { throw new webservice_access_exception(get_string('sitemaintenance', 'admin')); } //only confirmed user should be able to call web service if (!empty($user->deleted)) { add_to_log(SITEID, '', '', '', get_string('wsaccessuserdeleted', 'webservice', $user->username) . " - " . getremoteaddr(), 0, $user->id); throw new webservice_access_exception(get_string('wsaccessuserdeleted', 'webservice', $user->username)); } //only confirmed user should be able to call web service if (empty($user->confirmed)) { add_to_log(SITEID, '', '', '', get_string('wsaccessuserunconfirmed', 'webservice', $user->username) . " - " . getremoteaddr(), 0, $user->id); throw new webservice_access_exception(get_string('wsaccessuserunconfirmed', 'webservice', $user->username)); } //check the user is suspended if (!empty($user->suspended)) { add_to_log(SITEID, '', '', '', get_string('wsaccessusersuspended', 'webservice', $user->username) . " - " . getremoteaddr(), 0, $user->id); throw new webservice_access_exception(get_string('wsaccessusersuspended', 'webservice', $user->username)); } //retrieve the authentication plugin if no previously done if (empty($auth)) { $auth = get_auth_plugin($user->auth); } // check if credentials have expired if (!empty($auth->config->expiration) and $auth->config->expiration == 1) { $days2expire = $auth->password_expire($user->username); if (intval($days2expire) < 0) { add_to_log(SITEID, '', '', '', get_string('wsaccessuserexpired', 'webservice', $user->username) . " - " . getremoteaddr(), 0, $user->id); throw new webservice_access_exception(get_string('wsaccessuserexpired', 'webservice', $user->username)); } } //check if the auth method is nologin (in this case refuse connection) if ($user->auth == 'nologin') { add_to_log(SITEID, '', '', '', get_string('wsaccessusernologin', 'webservice', $user->username) . " - " . getremoteaddr(), 0, $user->id); throw new webservice_access_exception(get_string('wsaccessusernologin', 'webservice', $user->username)); } // now fake user login, the session is completely empty too enrol_check_plugins($user); session_set_user($user); $this->userid = $user->id; if ($this->authmethod != WEBSERVICE_AUTHMETHOD_SESSION_TOKEN && !has_capability("webservice/{$this->wsname}:use", $this->restricted_context)) { throw new webservice_access_exception(get_string('protocolnotallowed', 'webservice', $this->wsname)); } external_api::set_context_restriction($this->restricted_context); }
/** * Reset contents of all database tables to initial values, reset caches, etc. * * Note: this is relatively slow (cca 2 seconds for pg and 7 for mysql) - please use with care! * * @static * @param bool $logchanges log changes in global state and database in error log * @return void */ public static function reset_all_data($logchanges = false) { global $DB, $CFG, $USER, $SITE, $COURSE, $PAGE, $OUTPUT, $SESSION, $GROUPLIB_CACHE; // reset global $DB in case somebody mocked it $DB = self::get_global_backup('DB'); if ($DB->is_transaction_started()) { // we can not reset inside transaction $DB->force_transaction_rollback(); } $resetdb = self::reset_database(); $warnings = array(); if ($logchanges) { if ($resetdb) { $warnings[] = 'Warning: unexpected database modification, resetting DB state'; } $oldcfg = self::get_global_backup('CFG'); $oldsite = self::get_global_backup('SITE'); foreach ($CFG as $k => $v) { if (!property_exists($oldcfg, $k)) { $warnings[] = 'Warning: unexpected new $CFG->' . $k . ' value'; } else { if ($oldcfg->{$k} !== $CFG->{$k}) { $warnings[] = 'Warning: unexpected change of $CFG->' . $k . ' value'; } } unset($oldcfg->{$k}); } if ($oldcfg) { foreach ($oldcfg as $k => $v) { $warnings[] = 'Warning: unexpected removal of $CFG->' . $k; } } if ($USER->id != 0) { $warnings[] = 'Warning: unexpected change of $USER'; } if ($COURSE->id != $oldsite->id) { $warnings[] = 'Warning: unexpected change of $COURSE'; } } // restore original globals $_SERVER = self::get_global_backup('_SERVER'); $CFG = self::get_global_backup('CFG'); $SITE = self::get_global_backup('SITE'); $COURSE = $SITE; // reinitialise following globals $OUTPUT = new bootstrap_renderer(); $PAGE = new moodle_page(); $FULLME = null; $ME = null; $SCRIPT = null; $SESSION = new stdClass(); $_SESSION['SESSION'] =& $SESSION; // set fresh new not-logged-in user $user = new stdClass(); $user->id = 0; $user->mnethostid = $CFG->mnet_localhost_id; session_set_user($user); // reset all static caches accesslib_clear_all_caches(true); get_string_manager()->reset_caches(); events_get_handlers('reset'); textlib::reset_caches(); if (class_exists('repository')) { repository::reset_caches(); } $GROUPLIB_CACHE = null; //TODO MDL-25290: add more resets here and probably refactor them to new core function // purge dataroot directory self::reset_dataroot(); // restore original config once more in case resetting of caches changed CFG $CFG = self::get_global_backup('CFG'); // inform data generator self::get_data_generator()->reset(); // fix PHP settings error_reporting($CFG->debug); // verify db writes just in case something goes wrong in reset if (self::$lastdbwrites != $DB->perf_get_writes()) { error_log('Unexpected DB writes in phpunit_util::reset_all_data()'); self::$lastdbwrites = $DB->perf_get_writes(); } if ($warnings) { $warnings = implode("\n", $warnings); trigger_error($warnings, E_USER_WARNING); } }
//redirect to the 2.0 rss URL redirect($url); } else { // Authenticate the user from the token $userid = rss_get_userid_from_token($token); if (!$userid) { rss_error('rsserrorauth'); } } $user = get_complete_user_data('id', $userid); // let enrol plugins deal with new enrolments if necessary enrol_check_plugins($user); session_set_user($user); //for login and capability checks // Check the context actually exists list($context, $course, $cm) = get_context_info_array($contextid); if (!$context) { rss_error(); } $PAGE->set_context($context); try { $autologinguest = true; $setwantsurltome = true; $preventredirect = true; require_login($course, $autologinguest, $cm, $setwantsurltome, $preventredirect); } catch (Exception $e) {
/** * Reset contents of all database tables to initial values, reset caches, etc. * * Note: this is relatively slow (cca 2 seconds for pg and 7 for mysql) - please use with care! * * @static */ public static function reset_all_data() { global $DB, $CFG; $data = self::get_tabledata(); $trans = $DB->start_delegated_transaction(); // faster and safer foreach ($data as $table => $records) { $DB->delete_records($table, array()); $resetseq = null; foreach ($records as $record) { if (is_null($resetseq)) { $resetseq = property_exists($record, 'id'); } $DB->import_record($table, $record, false, true); } if ($resetseq === true) { $DB->get_manager()->reset_sequence($table, true); } } $trans->allow_commit(); purge_all_caches(); $user = new stdClass(); $user->id = 0; $user->mnet = 0; $user->mnethostid = $CFG->mnet_localhost_id; session_set_user($user); accesslib_clear_all_caches_for_unit_testing(); }
/** * Install Moodle DB, * config.php must exist, there must not be any tables in db yet. * * @param array $options adminpass is mandatory * @param bool $interactive * @return void */ function install_cli_database(array $options, $interactive) { global $CFG, $DB; require_once $CFG->libdir . '/environmentlib.php'; require_once $CFG->libdir . '/upgradelib.php'; // show as much debug as possible @error_reporting(E_ALL | E_STRICT); @ini_set('display_errors', '1'); $CFG->debug = E_ALL | E_STRICT; $CFG->debugdisplay = true; $CFG->version = ''; $CFG->release = ''; $CFG->branch = ''; $version = null; $release = null; $branch = null; // read $version and $release require $CFG->dirroot . '/version.php'; if ($DB->get_tables()) { cli_error(get_string('clitablesexist', 'install')); } if (empty($options['adminpass'])) { cli_error('Missing required admin password'); } // test environment first list($envstatus, $environment_results) = check_moodle_environment(normalize_version($release), ENV_SELECT_RELEASE); if (!$envstatus) { $errors = environment_get_errors($environment_results); cli_heading(get_string('environment', 'admin')); foreach ($errors as $error) { list($info, $report) = $error; echo "!! {$info} !!\n{$report}\n\n"; } exit(1); } if (!$DB->setup_is_unicodedb()) { if (!$DB->change_db_encoding()) { // If could not convert successfully, throw error, and prevent installation cli_error(get_string('unicoderequired', 'admin')); } } if ($interactive) { cli_separator(); cli_heading(get_string('databasesetup')); } // install core install_core($version, true); set_config('release', $release); set_config('branch', $branch); if (PHPUNIT_TEST) { // mark as test database as soon as possible set_config('phpunittest', 'na'); } // install all plugins types, local, etc. upgrade_noncore(true); // set up admin user password $DB->set_field('user', 'password', hash_internal_user_password($options['adminpass']), array('username' => 'admin')); // rename admin username if needed if (isset($options['adminuser']) and $options['adminuser'] !== 'admin' and $options['adminuser'] !== 'guest') { $DB->set_field('user', 'username', $options['adminuser'], array('username' => 'admin')); } // indicate that this site is fully configured set_config('rolesactive', 1); upgrade_finished(); // log in as admin - we need do anything when applying defaults $admins = get_admins(); $admin = reset($admins); session_set_user($admin); // apply all default settings, do it twice to fill all defaults - some settings depend on other setting admin_apply_default_settings(NULL, true); admin_apply_default_settings(NULL, true); set_config('registerauth', ''); // set the site name if (isset($options['shortname']) and $options['shortname'] !== '') { $DB->set_field('course', 'shortname', $options['shortname'], array('format' => 'site')); } if (isset($options['fullname']) and $options['fullname'] !== '') { $DB->set_field('course', 'fullname', $options['fullname'], array('format' => 'site')); } }
cli_heading(get_string('environment', 'admin')); foreach ($errors as $error) { list($info, $report) = $error; echo "!! {$info} !!\n{$report}\n\n"; } exit(1); } if ($interactive) { echo html_to_text(get_string('upgradesure', 'admin', $newversion)) . "\n"; $prompt = get_string('cliyesnoprompt', 'admin'); $input = cli_input($prompt, '', array(get_string('clianswerno', 'admin'), get_string('cliansweryes', 'admin'))); if ($input == get_string('clianswerno', 'admin')) { exit(1); } } if ($version > $CFG->version) { upgrade_core($version, true); } set_config('release', $release); // unconditionally upgrade upgrade_noncore(true); // log in as admin - we need doanything permission when applying defaults $admins = get_admins(); $admin = reset($admins); session_set_user($admin); // apply all default settings, just in case do it twice to fill all defaults admin_apply_default_settings(NULL, false); admin_apply_default_settings(NULL, false); echo get_string('cliupgradefinished', 'admin') . "\n"; exit(0); // 0 means success
require_once $CFG->libdir . '/adminlib.php'; function mdk_set_config($name, $value, $plugin = null) { set_config($name, $value, $plugin); $value = is_bool($value) ? (int) $value : $value; if ($plugin) { // Make a fancy name. $name = "{$plugin}/{$name}"; } mtrace("Setting {$name} to {$value}"); } // Load all the settings. if (class_exists('\\core\\session\\manager')) { \core\session\manager::set_user(get_admin()); } else { session_set_user(get_admin()); } $adminroot = admin_get_root(); // Debugging settings. $settingspage = $adminroot->locate('debugging', true); $settings = $settingspage->settings; // Set developer level. $default = $settings->debug->get_defaultsetting(); mdk_set_config('debug', $default); // Display debug messages. $default = $settings->debugdisplay->get_defaultsetting(); mdk_set_config('debugdisplay', $default); // Debug the performance. $default = $settings->perfdebug->get_defaultsetting(); mdk_set_config('perfdebug', $default); // Debug the information of the page.
function mnetadmin_rpc_upgrade($user, $json_response = true) { global $CFG, $USER; // Invoke local user and check his rights if ($auth_response = invoke_local_user((array) $user)) { if ($json_response) { return $auth_response; } else { return json_decode($auth_response); } } // Creating response $response = new stdclass(); $response->status = RPC_SUCCESS; require "{$CFG->dirroot}/version.php"; // defines $version, $release, $branch and $maturity $CFG->target_release = $release; // used during installation and upgrades if ($version < $CFG->version) { $response->status = RPC_FAILURE_RUN; $response->error = get_string('downgradedcore', 'error'); $response->errors[] = get_string('downgradedcore', 'error'); if ($json_response) { return json_encode($response); } else { return $response; } } $oldversion = "{$CFG->release} ({$CFG->version})"; $newversion = "{$release} ({$version})"; if (!moodle_needs_upgrading()) { $response->message = get_string('cliupgradenoneed', 'core_admin', $newversion); if ($json_response) { return json_encode($response); } else { return $response; } } // debug_trace('Remote Upgrade : Environment check'); list($envstatus, $environment_results) = check_moodle_environment(normalize_version($release), ENV_SELECT_NEWER); if (!$envstatus) { $response->status = RPC_FAILURE_RUN; $response->error = vmoodle_get_string('environmentissues', 'vmoodleadminset_upgrade'); $response->errors[] = vmoodle_get_string('environmentissues', 'vmoodleadminset_upgrade'); $response->detail = $environment_results; if ($json_response) { return json_encode($response); } else { return $response; } } // Test plugin dependencies. // debug_trace('Remote Upgrade : Plugins check'); $failed = array(); if (!plugin_manager::instance()->all_plugins_ok($version, $failed)) { $response->status = RPC_FAILURE_RUN; $response->error = get_string('pluginschecktodo', 'admin'); $response->errors[] = get_string('pluginschecktodo', 'admin'); if ($json_response) { return json_encode($response); } else { return $response; } } ob_start(); // debug_trace('Remote Upgrade : Upgrade core'); if ($version > $CFG->version) { upgrade_core($version, false); } set_config('release', $release); set_config('branch', $branch); // unconditionally upgrade // debug_trace('Remote Upgrade : Upgrade other'); upgrade_noncore(false); // log in as admin - we need doanything permission when applying defaults // debug_trace('Remote Upgrade : Turning ADMIN '); session_set_user(get_admin()); // apply all default settings, just in case do it twice to fill all defaults // debug_trace('Remote Upgrade : Applying settings '); admin_apply_default_settings(NULL, false); admin_apply_default_settings(NULL, false); ob_end_clean(); $response->message = vmoodle_get_string('upgradecomplete', 'vmoodleadminset_upgrade', $newversion); if ($json_response) { return json_encode($response); } else { return $response; } }
/** * Call to complete the user login process after authenticate_user_login() * has succeeded. It will setup the $USER variable and other required bits * and pieces. * * NOTE: * - It will NOT log anything -- up to the caller to decide what to log. * * @uses $CFG, $USER * @param string $user obj * @return object A {@link $USER} object - BC only, do not use */ function complete_user_login($user, $setcookie = true) { global $CFG, $USER, $SESSION; // check enrolments, load caps and setup $USER object session_set_user($user); update_user_login_times(); set_login_session_preferences(); if ($setcookie) { if (empty($CFG->nolastloggedin)) { set_moodle_cookie($USER->username); } else { // do not store last logged in user in cookie // auth plugins can temporarily override this from loginpage_hook() // do not save $CFG->nolastloggedin in database! set_moodle_cookie('nobody'); } } /// Select password change url $userauth = get_auth_plugin($USER->auth); /// check whether the user should be changing password if (get_user_preferences('auth_forcepasswordchange', false)) { if ($userauth->can_change_password()) { if ($changeurl = $userauth->change_password_url()) { redirect($changeurl); } else { redirect($CFG->httpswwwroot . '/login/change_password.php'); } } else { print_error('nopasswordchangeforced', 'auth'); } } return $USER; }
/** * Reset contents of all database tables to initial values, reset caches, etc. * * Note: this is relatively slow (cca 2 seconds for pg and 7 for mysql) - please use with care! * * @static * @param bool $logchanges log changes in global state and database in error log * @return void */ public static function reset_all_data($logchanges = false) { global $DB, $CFG, $USER, $SITE, $COURSE, $PAGE, $OUTPUT, $SESSION, $GROUPLIB_CACHE; // Release memory and indirectly call destroy() methods to release resource handles, etc. gc_collect_cycles(); // reset global $DB in case somebody mocked it $DB = self::get_global_backup('DB'); if ($DB->is_transaction_started()) { // we can not reset inside transaction $DB->force_transaction_rollback(); } $resetdb = self::reset_database(); $warnings = array(); if ($logchanges) { if ($resetdb) { $warnings[] = 'Warning: unexpected database modification, resetting DB state'; } $oldcfg = self::get_global_backup('CFG'); $oldsite = self::get_global_backup('SITE'); foreach($CFG as $k=>$v) { if (!property_exists($oldcfg, $k)) { $warnings[] = 'Warning: unexpected new $CFG->'.$k.' value'; } else if ($oldcfg->$k !== $CFG->$k) { $warnings[] = 'Warning: unexpected change of $CFG->'.$k.' value'; } unset($oldcfg->$k); } if ($oldcfg) { foreach($oldcfg as $k=>$v) { $warnings[] = 'Warning: unexpected removal of $CFG->'.$k; } } if ($USER->id != 0) { $warnings[] = 'Warning: unexpected change of $USER'; } if ($COURSE->id != $oldsite->id) { $warnings[] = 'Warning: unexpected change of $COURSE'; } } if (ini_get('max_execution_time') != 0) { // This is special warning for all resets because we do not want any // libraries to mess with timeouts unintentionally. // Our PHPUnit integration is not supposed to change it either. // TODO: MDL-38912 uncomment and fix all + somehow resolve timeouts in failed tests. //$warnings[] = 'Warning: max_execution_time was changed.'; set_time_limit(0); } // restore original globals $_SERVER = self::get_global_backup('_SERVER'); $CFG = self::get_global_backup('CFG'); $SITE = self::get_global_backup('SITE'); $COURSE = $SITE; // reinitialise following globals $OUTPUT = new bootstrap_renderer(); $PAGE = new moodle_page(); $FULLME = null; $ME = null; $SCRIPT = null; $SESSION = new stdClass(); $_SESSION['SESSION'] =& $SESSION; // set fresh new not-logged-in user $user = new stdClass(); $user->id = 0; $user->mnethostid = $CFG->mnet_localhost_id; session_set_user($user); // reset all static caches accesslib_clear_all_caches(true); get_string_manager()->reset_caches(); events_get_handlers('reset'); textlib::reset_caches(); if (class_exists('repository')) { repository::reset_caches(); } $GROUPLIB_CACHE = null; //TODO MDL-25290: add more resets here and probably refactor them to new core function // Reset course and module caches. $reset = 'reset'; get_fast_modinfo($reset); // Reset other singletons. if (class_exists('plugin_manager')) { plugin_manager::reset_caches(true); } if (class_exists('available_update_checker')) { available_update_checker::reset_caches(true); } // purge dataroot directory self::reset_dataroot(); // restore original config once more in case resetting of caches changed CFG $CFG = self::get_global_backup('CFG'); // inform data generator self::get_data_generator()->reset(); // fix PHP settings error_reporting($CFG->debug); // verify db writes just in case something goes wrong in reset if (self::$lastdbwrites != $DB->perf_get_writes()) { error_log('Unexpected DB writes in phpunit_util::reset_all_data()'); self::$lastdbwrites = $DB->perf_get_writes(); } if ($warnings) { $warnings = implode("\n", $warnings); trigger_error($warnings, E_USER_WARNING); } }
/** * Resets the test environment. * * @throws coding_exception If here we are not using the test database it should be because of a coding error * @BeforeScenario */ public function before_scenario($event) { global $DB, $SESSION, $CFG; // As many checks as we can. if (!defined('BEHAT_TEST') || !defined('BEHAT_SITE_RUNNING') || php_sapi_name() != 'cli' || !behat_util::is_test_mode_enabled() || !behat_util::is_test_site()) { throw new coding_exception('Behat only can modify the test database and the test dataroot!'); } try { $session = $this->getSession(); } catch (CurlExec $e) { // Exception thrown by WebDriver, so only @javascript tests will be caugth; in // behat_util::is_server_running() we already checked that the server is running. $moreinfo = 'More info in ' . behat_command::DOCS_URL . '#Running_tests'; $msg = 'Selenium server is not running, you need to start it to run tests that involve Javascript. ' . $moreinfo; throw new Exception($msg); } catch (UnknownError $e) { // Generic 'I have no idea' Selenium error. Custom exception to provide more feedback about possible solutions. $this->throw_unknown_exception($e); } // We need the Mink session to do it and we do it only before the first scenario. if (self::is_first_scenario()) { behat_selectors::register_moodle_selectors($session); } // Avoid some notices / warnings. $SESSION = new stdClass(); behat_util::reset_database(); behat_util::reset_dataroot(); accesslib_clear_all_caches(true); // Reset the nasty strings list used during the last test. nasty_strings::reset_used_strings(); // Assing valid data to admin user (some generator-related code needs a valid user). $user = $DB->get_record('user', array('username' => 'admin')); session_set_user($user); // Reset the browser if specified in config.php. if (!empty($CFG->behat_restart_browser_after) && $this->running_javascript()) { $now = time(); if (self::$lastbrowsersessionstart + $CFG->behat_restart_browser_after < $now) { $session->restart(); self::$lastbrowsersessionstart = $now; } } // Start always in the the homepage. try { // Let's be conservative as we never know when new upstream issues will affect us. $session->visit($this->locate_path('/')); } catch (UnknownError $e) { $this->throw_unknown_exception($e); } // Checking that the root path is a Moodle test site. if (self::is_first_scenario()) { $notestsiteexception = new Exception('The base URL (' . $CFG->wwwroot . ') is not a behat test site, ' . 'ensure you started the built-in web server in the correct directory or your web server is correctly started and set up'); $this->find("xpath", "//head/child::title[normalize-space(.)='" . behat_util::BEHATSITENAME . "']", $notestsiteexception); self::$initprocessesfinished = true; } }
/** * Resets the test environment. * * @throws coding_exception If here we are not using the test database it should be because of a coding error * @BeforeScenario */ public function before_scenario($event) { global $DB, $SESSION, $CFG; // As many checks as we can. if (!defined('BEHAT_TEST') || !defined('BEHAT_SITE_RUNNING') || php_sapi_name() != 'cli' || !behat_util::is_test_mode_enabled() || !behat_util::is_test_site()) { throw new coding_exception('Behat only can modify the test database and the test dataroot!'); } // Avoid some notices / warnings. $SESSION = new stdClass(); behat_util::reset_database(); behat_util::reset_dataroot(); purge_all_caches(); accesslib_clear_all_caches(true); // Reset the nasty strings list used during the last test. nasty_strings::reset_used_strings(); // Assing valid data to admin user (some generator-related code needs a valid user). $user = $DB->get_record('user', array('username' => 'admin')); session_set_user($user); // Start always in the the homepage. $this->getSession()->visit($this->locate_path('/')); }
/** * Call to complete the user login process after authenticate_user_login() * has succeeded. It will setup the $USER variable and other required bits * and pieces. * * NOTE: * - It will NOT log anything -- up to the caller to decide what to log. * - this function does not set any cookies any more! * * @param object $user * @return object A {@link $USER} object - BC only, do not use */ function complete_user_login($user) { global $CFG, $USER; // regenerate session id and delete old session, // this helps prevent session fixation attacks from the same domain session_regenerate_id(true); // let enrol plugins deal with new enrolments if necessary enrol_check_plugins($user); // check enrolments, load caps and setup $USER object session_set_user($user); // reload preferences from DB unset($USER->preference); check_user_preferences_loaded($USER); // update login times update_user_login_times(); // extra session prefs init set_login_session_preferences(); if (isguestuser()) { // no need to continue when user is THE guest return $USER; } /// Select password change url $userauth = get_auth_plugin($USER->auth); /// check whether the user should be changing password if (get_user_preferences('auth_forcepasswordchange', false)) { if ($userauth->can_change_password()) { if ($changeurl = $userauth->change_password_url()) { redirect($changeurl); } else { redirect($CFG->httpswwwroot . '/login/change_password.php'); } } else { print_error('nopasswordchangeforced', 'auth'); } } return $USER; }
/** * Call to complete the user login process after authenticate_user_login() * has succeeded. It will setup the $USER variable and other required bits * and pieces. * * NOTE: * - It will NOT log anything -- up to the caller to decide what to log. * * @param object $user * @param bool $setcookie * @return object A {@link $USER} object - BC only, do not use */ function complete_user_login($user, $setcookie = true) { global $CFG, $USER; // regenerate session id and delete old session, // this helps prevent session fixation attacks from the same domain session_regenerate_id(true); // check enrolments, load caps and setup $USER object session_set_user($user); // reload preferences from DB unset($user->preference); check_user_preferences_loaded($user); // update login times update_user_login_times(); // extra session prefs init set_login_session_preferences(); if (isguestuser()) { // no need to continue when user is THE guest return $USER; } if ($setcookie) { if (empty($CFG->nolastloggedin)) { set_moodle_cookie($USER->username); } else { // do not store last logged in user in cookie // auth plugins can temporarily override this from loginpage_hook() // do not save $CFG->nolastloggedin in database! set_moodle_cookie(''); } } /// Select password change url $userauth = get_auth_plugin($USER->auth); /// check whether the user should be changing password if (get_user_preferences('auth_forcepasswordchange', false)) { if ($userauth->can_change_password()) { if ($changeurl = $userauth->change_password_url()) { redirect($changeurl); } else { redirect($CFG->httpswwwroot . '/login/change_password.php'); } } else { print_error('nopasswordchangeforced', 'auth'); } } return $USER; }
/** * Initialise $USER object, handles google access * and sets up not logged in user properly. * * @return void */ protected function check_user_initialised() { if (isset($_SESSION['USER']->id)) { // already set up $USER return; } $user = null; if (!empty($CFG->opentogoogle) and !NO_MOODLE_COOKIES) { if (!empty($_SERVER['HTTP_USER_AGENT'])) { // allow web spiders in as guest users if (strpos($_SERVER['HTTP_USER_AGENT'], 'Googlebot') !== false) { $user = guest_user(); } else { if (strpos($_SERVER['HTTP_USER_AGENT'], 'google.com') !== false) { // Google $user = guest_user(); } else { if (strpos($_SERVER['HTTP_USER_AGENT'], 'Yahoo! Slurp') !== false) { // Yahoo $user = guest_user(); } else { if (strpos($_SERVER['HTTP_USER_AGENT'], '[ZSEBOT]') !== false) { // Zoomspider $user = guest_user(); } else { if (strpos($_SERVER['HTTP_USER_AGENT'], 'MSNBOT') !== false) { // MSN Search $user = guest_user(); } } } } } } if (!empty($CFG->guestloginbutton) and !$user and !empty($_SERVER['HTTP_REFERER'])) { // automaticaly log in users coming from search engine results if (strpos($_SERVER['HTTP_REFERER'], 'google') !== false) { $user = guest_user(); } else { if (strpos($_SERVER['HTTP_REFERER'], 'altavista') !== false) { $user = guest_user(); } } } } if (!$user) { $user = new object(); $user->id = 0; // to enable proper function of $CFG->notloggedinroleid hack if (isset($CFG->mnet_localhost_id)) { $user->mnethostid = $CFG->mnet_localhost_id; } else { $user->mnethostid = 1; } } session_set_user($user); }
/** * Initialise $USER object, handles google access * and sets up not logged in user properly. * * @return void */ protected function check_user_initialised() { global $CFG; if (isset($_SESSION['USER']->id)) { // already set up $USER return; } $user = null; if (!empty($CFG->opentogoogle) and !NO_MOODLE_COOKIES) { if (is_web_crawler()) { $user = guest_user(); } if (!empty($CFG->guestloginbutton) and !$user and !empty($_SERVER['HTTP_REFERER'])) { // automaticaly log in users coming from search engine results if (strpos($_SERVER['HTTP_REFERER'], 'google') !== false) { $user = guest_user(); } else { if (strpos($_SERVER['HTTP_REFERER'], 'altavista') !== false) { $user = guest_user(); } } } } if (!$user) { $user = new stdClass(); $user->id = 0; // to enable proper function of $CFG->notloggedinroleid hack if (isset($CFG->mnet_localhost_id)) { $user->mnethostid = $CFG->mnet_localhost_id; } else { $user->mnethostid = 1; } } session_set_user($user); }
/** * Set current $USER, reset access cache. * @static * @param null|int|stdClass $user user record, null or 0 means non-logged-in, positive integer means userid * @return void */ public static function setUser($user = null) { global $CFG, $DB; if (is_object($user)) { $user = clone $user; } else { if (!$user) { $user = new stdClass(); $user->id = 0; $user->mnethostid = $CFG->mnet_localhost_id; } else { $user = $DB->get_record('user', array('id' => $user)); } } unset($user->description); unset($user->access); unset($user->preference); session_set_user($user); }
} // Set the default site locale, a lot of the stuff may depend on this // it is definitely too late to call this first in require_login()! moodle_setlocale(); if (!empty($CFG->debugvalidators) and !empty($CFG->guestloginbutton)) { if ($CFG->theme == 'standard' or $CFG->theme == 'standardwhite') { // Temporary measure to help with XHTML validation if (isset($_SERVER['HTTP_USER_AGENT']) and empty($USER->id)) { // Allow W3CValidator in as user called w3cvalidator (or guest) if (strpos($_SERVER['HTTP_USER_AGENT'], 'W3C_Validator') !== false or strpos($_SERVER['HTTP_USER_AGENT'], 'Cynthia') !== false) { if ($user = get_complete_user_data("username", "w3cvalidator")) { $user->ignoresesskey = true; } else { $user = guest_user(); } session_set_user($user); } } } } // Apache log integration. In apache conf file one can use ${MOODULEUSER}n in // LogFormat to get the current logged in username in moodle. if ($USER && function_exists('apache_note') && !empty($CFG->apacheloguser) && isset($USER->username)) { $apachelog_userid = $USER->id; $apachelog_username = clean_filename($USER->username); $apachelog_name = ''; if (isset($USER->firstname)) { // We can assume both will be set // - even if to empty. $apachelog_name = clean_filename($USER->firstname . " " . $USER->lastname); }
/** * Reset contents of all database tables to initial values, reset caches, etc. * * Note: this is relatively slow (cca 2 seconds for pg and 7 for mysql) - please use with care! * * @static * @param bool $logchanges log changes in global state and database in error log * @return void */ public static function reset_all_data($logchanges = false) { global $DB, $CFG, $USER, $SITE, $COURSE, $PAGE, $OUTPUT, $SESSION; // Stop any message redirection. phpunit_util::stop_message_redirection(); // Release memory and indirectly call destroy() methods to release resource handles, etc. gc_collect_cycles(); // Show any unhandled debugging messages, the runbare() could already reset it. self::display_debugging_messages(); self::reset_debugging(); // reset global $DB in case somebody mocked it $DB = self::get_global_backup('DB'); if ($DB->is_transaction_started()) { // we can not reset inside transaction $DB->force_transaction_rollback(); } $resetdb = self::reset_database(); $warnings = array(); if ($logchanges) { if ($resetdb) { $warnings[] = 'Warning: unexpected database modification, resetting DB state'; } $oldcfg = self::get_global_backup('CFG'); $oldsite = self::get_global_backup('SITE'); foreach ($CFG as $k => $v) { if (!property_exists($oldcfg, $k)) { $warnings[] = 'Warning: unexpected new $CFG->' . $k . ' value'; } else { if ($oldcfg->{$k} !== $CFG->{$k}) { $warnings[] = 'Warning: unexpected change of $CFG->' . $k . ' value'; } } unset($oldcfg->{$k}); } if ($oldcfg) { foreach ($oldcfg as $k => $v) { $warnings[] = 'Warning: unexpected removal of $CFG->' . $k; } } if ($USER->id != 0) { $warnings[] = 'Warning: unexpected change of $USER'; } if ($COURSE->id != $oldsite->id) { $warnings[] = 'Warning: unexpected change of $COURSE'; } } // restore original globals $_SERVER = self::get_global_backup('_SERVER'); $CFG = self::get_global_backup('CFG'); $SITE = self::get_global_backup('SITE'); $COURSE = $SITE; // reinitialise following globals $OUTPUT = new bootstrap_renderer(); $PAGE = new moodle_page(); $FULLME = null; $ME = null; $SCRIPT = null; $SESSION = new stdClass(); $_SESSION['SESSION'] =& $SESSION; // set fresh new not-logged-in user $user = new stdClass(); $user->id = 0; $user->mnethostid = $CFG->mnet_localhost_id; session_set_user($user); // reset all static caches accesslib_clear_all_caches(true); get_string_manager()->reset_caches(true); reset_text_filters_cache(true); events_get_handlers('reset'); textlib::reset_caches(); if (class_exists('repository')) { repository::reset_caches(); } filter_manager::reset_caches(); //TODO MDL-25290: add more resets here and probably refactor them to new core function // Reset course and module caches. if (class_exists('format_base')) { // If file containing class is not loaded, there is no cache there anyway. format_base::reset_course_cache(0); } get_fast_modinfo(0, 0, true); // Reset other singletons. if (class_exists('plugin_manager')) { plugin_manager::reset_caches(true); } if (class_exists('available_update_checker')) { available_update_checker::reset_caches(true); } if (class_exists('available_update_deployer')) { available_update_deployer::reset_caches(true); } // purge dataroot directory self::reset_dataroot(); // restore original config once more in case resetting of caches changed CFG $CFG = self::get_global_backup('CFG'); // inform data generator self::get_data_generator()->reset(); // fix PHP settings error_reporting($CFG->debug); // verify db writes just in case something goes wrong in reset if (self::$lastdbwrites != $DB->perf_get_writes()) { error_log('Unexpected DB writes in phpunit_util::reset_all_data()'); self::$lastdbwrites = $DB->perf_get_writes(); } if ($warnings) { $warnings = implode("\n", $warnings); trigger_error($warnings, E_USER_WARNING); } }