public function test_get_user() { global $CFG; $this->resetAfterTest(true); // Create user and try fetach it with api. $user = $this->getDataGenerator()->create_user(); $this->assertEquals($user, core_user::get_user($user->id, '*', MUST_EXIST)); // Test noreply user. $CFG->noreplyuserid = null; $noreplyuser = core_user::get_noreply_user(); $this->assertEquals(1, $noreplyuser->emailstop); $this->assertFalse(core_user::is_real_user($noreplyuser->id)); $this->assertEquals($CFG->noreplyaddress, $noreplyuser->email); $this->assertEquals(get_string('noreplyname'), $noreplyuser->firstname); // Set user as noreply user and make sure noreply propery is set. core_user::reset_internal_users(); $CFG->noreplyuserid = $user->id; $noreplyuser = core_user::get_noreply_user(); $this->assertEquals(1, $noreplyuser->emailstop); $this->assertTrue(core_user::is_real_user($noreplyuser->id)); // Test support user. core_user::reset_internal_users(); $CFG->supportemail = null; $CFG->noreplyuserid = null; $supportuser = core_user::get_support_user(); $adminuser = get_admin(); $this->assertEquals($adminuser, $supportuser); $this->assertTrue(core_user::is_real_user($supportuser->id)); // When supportemail is set. core_user::reset_internal_users(); $CFG->supportemail = '*****@*****.**'; $supportuser = core_user::get_support_user(); $this->assertEquals(core_user::SUPPORT_USER, $supportuser->id); $this->assertFalse(core_user::is_real_user($supportuser->id)); // Set user as support user and make sure noreply propery is set. core_user::reset_internal_users(); $CFG->supportuserid = $user->id; $supportuser = core_user::get_support_user(); $this->assertEquals($user, $supportuser); $this->assertTrue(core_user::is_real_user($supportuser->id)); }
$currentuser = false; //if we're looking at someone else's messages we need to lock/remove some UI elements $showactionlinks = false; } else { $user1 = $USER; } unset($user1id); $user2 = null; if (!empty($user2id)) { $user2 = core_user::get_user($user2id); if (!$user2) { print_error('invaliduserid'); } } unset($user2id); $user2realuser = !empty($user2) && core_user::is_real_user($user2->id); $showactionlinks = $showactionlinks && $user2realuser; $systemcontext = context_system::instance(); if ($currentuser === false && !has_capability('moodle/site:readallmessages', $systemcontext)) { print_error('accessdenied', 'admin'); } if (substr($viewing, 0, 7) == MESSAGE_VIEW_COURSE) { $courseid = intval(substr($viewing, 7)); require_login($courseid); require_capability('moodle/course:viewparticipants', context_course::instance($courseid)); $PAGE->set_pagelayout('incourse'); } else { $PAGE->set_pagelayout('standard'); $PAGE->set_context(context_user::instance($user1->id)); } if (!empty($user1->id) && $user1->id != $USER->id) {
/** * Get messages function implementation. * * @since 2.8 * @throws invalid_parameter_exception * @throws moodle_exception * @param int $useridto the user id who received the message * @param int $useridfrom the user id who send the message. -10 or -20 for no-reply or support user * @param string $type type of message to return, expected values: notifications, conversations and both * @param bool $read true for retreiving read messages, false for unread * @param bool $newestfirst true for ordering by newest first, false for oldest first * @param int $limitfrom limit from * @param int $limitnum limit num * @return external_description */ public static function get_messages($useridto, $useridfrom = 0, $type = 'both', $read = true, $newestfirst = true, $limitfrom = 0, $limitnum = 0) { global $CFG, $USER; $warnings = array(); $params = array('useridto' => $useridto, 'useridfrom' => $useridfrom, 'type' => $type, 'read' => $read, 'newestfirst' => $newestfirst, 'limitfrom' => $limitfrom, 'limitnum' => $limitnum); $params = self::validate_parameters(self::get_messages_parameters(), $params); $context = context_system::instance(); self::validate_context($context); $useridto = $params['useridto']; $useridfrom = $params['useridfrom']; $type = $params['type']; $read = $params['read']; $newestfirst = $params['newestfirst']; $limitfrom = $params['limitfrom']; $limitnum = $params['limitnum']; $allowedvalues = array('notifications', 'conversations', 'both'); if (!in_array($type, $allowedvalues)) { throw new invalid_parameter_exception('Invalid value for type parameter (value: ' . $type . '),' . 'allowed values are: ' . implode(',', $allowedvalues)); } // Check if private messaging between users is allowed. if (empty($CFG->messaging)) { // If we are retreiving only conversations, and messaging is disabled, throw an exception. if ($type == "conversations") { throw new moodle_exception('disabled', 'message'); } if ($type == "both") { $warning = array(); $warning['item'] = 'message'; $warning['itemid'] = $USER->id; $warning['warningcode'] = '1'; $warning['message'] = 'Private messages (conversations) are not enabled in this site. Only notifications will be returned'; $warnings[] = $warning; } } if (!empty($useridto)) { if (core_user::is_real_user($useridto)) { $userto = core_user::get_user($useridto, '*', MUST_EXIST); } else { throw new moodle_exception('invaliduser'); } } if (!empty($useridfrom)) { // We use get_user here because the from user can be the noreply or support user. $userfrom = core_user::get_user($useridfrom, '*', MUST_EXIST); } // Check if the current user is the sender/receiver or just a privileged user. if ($useridto != $USER->id and $useridfrom != $USER->id and !has_capability('moodle/site:readallmessages', $context)) { throw new moodle_exception('accessdenied', 'admin'); } // Which type of messages to retrieve. $notifications = -1; if ($type != 'both') { $notifications = $type == 'notifications' ? 1 : 0; } $orderdirection = $newestfirst ? 'DESC' : 'ASC'; $sort = "mr.timecreated {$orderdirection}"; if ($messages = message_get_messages($useridto, $useridfrom, $notifications, $read, $sort, $limitfrom, $limitnum)) { $canviewfullname = has_capability('moodle/site:viewfullnames', $context); // In some cases, we don't need to get the to/from user objects from the sql query. $userfromfullname = ''; $usertofullname = ''; // In this case, the useridto field is not empty, so we can get the user destinatary fullname from there. if (!empty($useridto)) { $usertofullname = fullname($userto, $canviewfullname); // The user from may or may not be filled. if (!empty($useridfrom)) { $userfromfullname = fullname($userfrom, $canviewfullname); } } else { // If the useridto field is empty, the useridfrom must be filled. $userfromfullname = fullname($userfrom, $canviewfullname); } foreach ($messages as $mid => $message) { // Do not return deleted messages. if ($useridto == $USER->id and $message->timeusertodeleted or $useridfrom == $USER->id and $message->timeuserfromdeleted) { unset($messages[$mid]); continue; } // We need to get the user from the query. if (empty($userfromfullname)) { // Check for non-reply and support users. if (core_user::is_real_user($message->useridfrom)) { $user = new stdClass(); $user = username_load_fields_from_object($user, $message, 'userfrom'); $message->userfromfullname = fullname($user, $canviewfullname); } else { $user = core_user::get_user($message->useridfrom); $message->userfromfullname = fullname($user, $canviewfullname); } } else { $message->userfromfullname = $userfromfullname; } // We need to get the user from the query. if (empty($usertofullname)) { $user = new stdClass(); $user = username_load_fields_from_object($user, $message, 'userto'); $message->usertofullname = fullname($user, $canviewfullname); } else { $message->usertofullname = $usertofullname; } // This field is only available in the message_read table. if (!isset($message->timeread)) { $message->timeread = 0; } $message->text = message_format_message_text($message); $messages[$mid] = (array) $message; } } $results = array('messages' => $messages, 'warnings' => $warnings); return $results; }
/** * Called when a message provider wants to send a message. * This functions checks the message recipient's message processor configuration then * sends the message to the configured processors * * Required parameters of the $eventdata object: * component string component name. must exist in message_providers * name string message type name. must exist in message_providers * userfrom object|int the user sending the message * userto object|int the message recipient * subject string the message subject * fullmessage string the full message in a given format * fullmessageformat int the format if the full message (FORMAT_MOODLE, FORMAT_HTML, ..) * fullmessagehtml string the full version (the message processor will choose with one to use) * smallmessage string the small version of the message * * Optional parameters of the $eventdata object: * notification bool should the message be considered as a notification rather than a personal message * contexturl string if this is a notification then you can specify a url to view the event. For example the forum post the user is being notified of. * contexturlname string the display text for contexturl * * Note: processor failure is is not reported as false return value, * earlier versions did not do it consistently either. * * @todo MDL-55449 Drop support for stdClass in Moodle 3.6 * @category message * @param \core\message\message $eventdata information about the message (component, userfrom, userto, ...) * @return mixed the integer ID of the new message or false if there was a problem with submitted data */ function message_send($eventdata) { global $CFG, $DB; // TODO MDL-55449 Drop support for stdClass in Moodle 3.6. if ($eventdata instanceof \stdClass) { if (!isset($eventdata->courseid)) { $eventdata->courseid = null; } debugging('eventdata as \stdClass is deprecated. Please use core\message\message instead.', DEBUG_DEVELOPER); } //new message ID to return $messageid = false; // Fetch default (site) preferences $defaultpreferences = get_message_output_default_preferences(); $preferencebase = $eventdata->component.'_'.$eventdata->name; // If message provider is disabled then don't do any processing. if (!empty($defaultpreferences->{$preferencebase.'_disable'})) { return $messageid; } // By default a message is a notification. Only personal/private messages aren't notifications. if (!isset($eventdata->notification)) { $eventdata->notification = 1; } if (!is_object($eventdata->userto)) { $eventdata->userto = core_user::get_user($eventdata->userto); } if (!is_object($eventdata->userfrom)) { $eventdata->userfrom = core_user::get_user($eventdata->userfrom); } if (!$eventdata->userto) { debugging('Attempt to send msg to unknown user', DEBUG_NORMAL); return false; } if (!$eventdata->userfrom) { debugging('Attempt to send msg from unknown user', DEBUG_NORMAL); return false; } // Verify all necessary data fields are present. if (!isset($eventdata->userto->auth) or !isset($eventdata->userto->suspended) or !isset($eventdata->userto->deleted) or !isset($eventdata->userto->emailstop)) { debugging('Necessary properties missing in userto object, fetching full record', DEBUG_DEVELOPER); $eventdata->userto = core_user::get_user($eventdata->userto->id); } $usertoisrealuser = (core_user::is_real_user($eventdata->userto->id) != false); // If recipient is internal user (noreply user), and emailstop is set then don't send any msg. if (!$usertoisrealuser && !empty($eventdata->userto->emailstop)) { debugging('Attempt to send msg to internal (noreply) user', DEBUG_NORMAL); return false; } //after how long inactive should the user be considered logged off? if (isset($CFG->block_online_users_timetosee)) { $timetoshowusers = $CFG->block_online_users_timetosee * 60; } else { $timetoshowusers = 300;//5 minutes } // Work out if the user is logged in or not if (!empty($eventdata->userto->lastaccess) && (time()-$timetoshowusers) < $eventdata->userto->lastaccess) { $userstate = 'loggedin'; } else { $userstate = 'loggedoff'; } // Create the message object $savemessage = new stdClass(); $savemessage->courseid = $eventdata->courseid; $savemessage->useridfrom = $eventdata->userfrom->id; $savemessage->useridto = $eventdata->userto->id; $savemessage->subject = $eventdata->subject; $savemessage->fullmessage = $eventdata->fullmessage; $savemessage->fullmessageformat = $eventdata->fullmessageformat; $savemessage->fullmessagehtml = $eventdata->fullmessagehtml; $savemessage->smallmessage = $eventdata->smallmessage; $savemessage->notification = $eventdata->notification; $savemessage->eventtype = $eventdata->name; $savemessage->component = $eventdata->component; if (!empty($eventdata->contexturl)) { $savemessage->contexturl = (string)$eventdata->contexturl; } else { $savemessage->contexturl = null; } if (!empty($eventdata->contexturlname)) { $savemessage->contexturlname = (string)$eventdata->contexturlname; } else { $savemessage->contexturlname = null; } $savemessage->timecreated = time(); if (PHPUNIT_TEST and class_exists('phpunit_util')) { // Add some more tests to make sure the normal code can actually work. $componentdir = core_component::get_component_directory($eventdata->component); if (!$componentdir or !is_dir($componentdir)) { throw new coding_exception('Invalid component specified in message-send(): '.$eventdata->component); } if (!file_exists("$componentdir/db/messages.php")) { throw new coding_exception("$eventdata->component does not contain db/messages.php necessary for message_send()"); } $messageproviders = null; include("$componentdir/db/messages.php"); if (!isset($messageproviders[$eventdata->name])) { throw new coding_exception("Missing messaging defaults for event '$eventdata->name' in '$eventdata->component' messages.php file"); } unset($componentdir); unset($messageproviders); // Now ask phpunit if it wants to catch this message. if (phpunit_util::is_redirecting_messages()) { $savemessage->timeread = time(); $messageid = $DB->insert_record('message_read', $savemessage); $message = $DB->get_record('message_read', array('id'=>$messageid)); phpunit_util::message_sent($message); return $messageid; } } // Fetch enabled processors $processors = get_message_processors(true); // Preset variables $processorlist = array(); // Fill in the array of processors to be used based on default and user preferences foreach ($processors as $processor) { // Skip adding processors for internal user, if processor doesn't support sending message to internal user. if (!$usertoisrealuser && !$processor->object->can_send_to_any_users()) { continue; } // First find out permissions $defaultpreference = $processor->name.'_provider_'.$preferencebase.'_permitted'; if (isset($defaultpreferences->{$defaultpreference})) { $permitted = $defaultpreferences->{$defaultpreference}; } else { // MDL-25114 They supplied an $eventdata->component $eventdata->name combination which doesn't // exist in the message_provider table (thus there is no default settings for them). $preferrormsg = "Could not load preference $defaultpreference. Make sure the component and name you supplied to message_send() are valid."; throw new coding_exception($preferrormsg); } // Find out if user has configured this output // Some processors cannot function without settings from the user $userisconfigured = $processor->object->is_user_configured($eventdata->userto); // DEBUG: notify if we are forcing unconfigured output if ($permitted == 'forced' && !$userisconfigured) { debugging('Attempt to force message delivery to user who has "'.$processor->name.'" output unconfigured', DEBUG_NORMAL); } // Populate the list of processors we will be using if ($permitted == 'forced' && $userisconfigured) { // An admin is forcing users to use this message processor. Use this processor unconditionally. $processorlist[] = $processor->name; } else if ($permitted == 'permitted' && $userisconfigured && !$eventdata->userto->emailstop) { // User has not disabled notifications // See if user set any notification preferences, otherwise use site default ones $userpreferencename = 'message_provider_'.$preferencebase.'_'.$userstate; if ($userpreference = get_user_preferences($userpreferencename, null, $eventdata->userto)) { if (in_array($processor->name, explode(',', $userpreference))) { $processorlist[] = $processor->name; } } else if (isset($defaultpreferences->{$userpreferencename})) { if (in_array($processor->name, explode(',', $defaultpreferences->{$userpreferencename}))) { $processorlist[] = $processor->name; } } } } // Only cache messages, not notifications. if (empty($savemessage->notification)) { // Cache the timecreated value of the last message between these two users. $cache = cache::make('core', 'message_time_last_message_between_users'); $key = \core_message\helper::get_last_message_time_created_cache_key($savemessage->useridfrom, $savemessage->useridto); $cache->set($key, $savemessage->timecreated); } // Store unread message just in case we get a fatal error any time later. $savemessage->id = $DB->insert_record('message', $savemessage); $eventdata->savedmessageid = $savemessage->id; // Let the manager do the sending or buffering when db transaction in progress. return \core\message\manager::send_message($eventdata, $savemessage, $processorlist); }
* * @package core_user * @copyright 2015 Frédéric Massart - FMCorz.net * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ require_once __DIR__ . '/../config.php'; require_once $CFG->libdir . '/navigationlib.php'; require_login(null, false); if (isguestuser()) { throw new require_login_exception('Guests are not allowed here.'); } $userid = optional_param('userid', $USER->id, PARAM_INT); $currentuser = $userid == $USER->id; // Check that the user is a valid user. $user = core_user::get_user($userid); if (!$user || !core_user::is_real_user($userid)) { throw new moodle_exception('invaliduser', 'error'); } $PAGE->set_context(context_user::instance($userid)); $PAGE->set_url('/user/preferences.php', array('userid' => $userid)); $PAGE->set_pagelayout('admin'); $PAGE->set_pagetype('user-preferences'); $PAGE->set_title(get_string('preferences')); $PAGE->set_heading(fullname($user)); if (!$currentuser) { $PAGE->navigation->extend_for_user($user); // Need to check that settings exist. if ($settings = $PAGE->settingsnav->find('userviewingsettings' . $user->id, null)) { $settings->make_active(); } $url = new moodle_url('/user/preferences.php', array('userid' => $userid));
/** * Print a row of contactlist displaying user picture, messages waiting and * block links etc * * @param object $contact contact object containing all fields required for $OUTPUT->user_picture() * @param bool $incontactlist is the user a contact of ours? * @param bool $isblocked is the user blocked? * @param string $selectcontacturl the url to send the user to when a contact's name is clicked * @param bool $showactionlinks display action links next to the other users (add contact, block user etc) * @param object $selecteduser the user the current user is viewing (if any). They will be highlighted. * @return void */ function message_print_contactlist_user($contact, $incontactlist = true, $isblocked = false, $selectcontacturl = null, $showactionlinks = true, $selecteduser=null) { global $OUTPUT, $USER, $COURSE; $fullname = fullname($contact); $fullnamelink = $fullname; $output = ''; $linkclass = ''; if (!empty($selecteduser) && $contact->id == $selecteduser->id) { $linkclass = 'messageselecteduser'; } // Are there any unread messages for this contact? if ($contact->messagecount > 0 ){ $fullnamelink = '<strong>'.$fullnamelink.' ('.$contact->messagecount.')</strong>'; } $strcontact = $strblock = $strhistory = null; if ($showactionlinks) { // Show block and delete links if user is real user. if (core_user::is_real_user($contact->id)) { $strcontact = message_get_contact_add_remove_link($incontactlist, $isblocked, $contact); $strblock = message_get_contact_block_link($incontactlist, $isblocked, $contact); } $strhistory = message_history_link($USER->id, $contact->id, true, '', '', 'icon'); } $output .= html_writer::start_tag('div', array('class' => 'pix')); $output .= $OUTPUT->user_picture($contact, array('size' => 20, 'courseid' => $COURSE->id)); $output .= html_writer::end_tag('div'); $popupoptions = array( 'height' => MESSAGE_DISCUSSION_HEIGHT, 'width' => MESSAGE_DISCUSSION_WIDTH, 'menubar' => false, 'location' => false, 'status' => true, 'scrollbars' => true, 'resizable' => true); $link = $action = null; if (!empty($selectcontacturl)) { $link = new moodle_url($selectcontacturl.'&user2='.$contact->id); } else { //can $selectcontacturl be removed and maybe the be removed and hardcoded? $link = new moodle_url("/message/index.php?id=$contact->id"); $action = new popup_action('click', $link, "message_$contact->id", $popupoptions); } if (strlen($strcontact . $strblock . $strhistory) > 0) { $output .= html_writer::tag('div', $strcontact . $strblock . $strhistory, array('class' => 'link')); $output .= html_writer::start_tag('div', array('class' => 'contact')); $linkattr = array('class' => $linkclass, 'title' => get_string('sendmessageto', 'message', $fullname)); $output .= $OUTPUT->action_link($link, $fullnamelink, $action, $linkattr); $output .= html_writer::end_tag('div'); } else { $output .= html_writer::start_tag('div', array('class' => 'contact nolinks')); $linkattr = array('class' => $linkclass, 'title' => get_string('sendmessageto', 'message', $fullname)); $output .= $OUTPUT->action_link($link, $fullnamelink, $action, $linkattr); $output .= html_writer::end_tag('div'); } return $output; }
/** * Called when a message provider wants to send a message. * This functions checks the message recipient's message processor configuration then * sends the message to the configured processors * * Required parameters of the $eventdata object: * component string component name. must exist in message_providers * name string message type name. must exist in message_providers * userfrom object|int the user sending the message * userto object|int the message recipient * subject string the message subject * fullmessage string the full message in a given format * fullmessageformat int the format if the full message (FORMAT_MOODLE, FORMAT_HTML, ..) * fullmessagehtml string the full version (the message processor will choose with one to use) * smallmessage string the small version of the message * * Optional parameters of the $eventdata object: * notification bool should the message be considered as a notification rather than a personal message * contexturl string if this is a notification then you can specify a url to view the event. For example the forum post the user is being notified of. * contexturlname string the display text for contexturl * * @category message * @param object $eventdata information about the message (component, userfrom, userto, ...) * @return mixed the integer ID of the new message or false if there was a problem with a processor */ function message_send($eventdata) { global $CFG, $DB; //new message ID to return $messageid = false; // Fetch default (site) preferences $defaultpreferences = get_message_output_default_preferences(); $preferencebase = $eventdata->component . '_' . $eventdata->name; // If message provider is disabled then don't do any processing. if (!empty($defaultpreferences->{$preferencebase . '_disable'})) { return $messageid; } //TODO: we need to solve problems with database transactions here somehow, for now we just prevent transactions - sorry $DB->transactions_forbidden(); // By default a message is a notification. Only personal/private messages aren't notifications. if (!isset($eventdata->notification)) { $eventdata->notification = 1; } if (is_number($eventdata->userto)) { $eventdata->userto = core_user::get_user($eventdata->userto); } if (is_int($eventdata->userfrom)) { $eventdata->userfrom = core_user::get_user($eventdata->userfrom); } $usertoisrealuser = core_user::is_real_user($eventdata->userto->id) != false; // If recipient is internal user (noreply user), and emailstop is set then don't send any msg. if (!$usertoisrealuser && !empty($eventdata->userto->emailstop)) { debugging('Attempt to send msg to internal (noreply) user', DEBUG_NORMAL); return false; } if (!isset($eventdata->userto->auth) or !isset($eventdata->userto->suspended) or !isset($eventdata->userto->deleted)) { $eventdata->userto = core_user::get_user($eventdata->userto->id); } //after how long inactive should the user be considered logged off? if (isset($CFG->block_online_users_timetosee)) { $timetoshowusers = $CFG->block_online_users_timetosee * 60; } else { $timetoshowusers = 300; //5 minutes } // Work out if the user is logged in or not if (!empty($eventdata->userto->lastaccess) && time() - $timetoshowusers < $eventdata->userto->lastaccess) { $userstate = 'loggedin'; } else { $userstate = 'loggedoff'; } // Create the message object $savemessage = new stdClass(); $savemessage->useridfrom = $eventdata->userfrom->id; $savemessage->useridto = $eventdata->userto->id; $savemessage->subject = $eventdata->subject; $savemessage->fullmessage = $eventdata->fullmessage; $savemessage->fullmessageformat = $eventdata->fullmessageformat; $savemessage->fullmessagehtml = $eventdata->fullmessagehtml; $savemessage->smallmessage = $eventdata->smallmessage; $savemessage->notification = $eventdata->notification; if (!empty($eventdata->contexturl)) { $savemessage->contexturl = $eventdata->contexturl; } else { $savemessage->contexturl = null; } if (!empty($eventdata->contexturlname)) { $savemessage->contexturlname = $eventdata->contexturlname; } else { $savemessage->contexturlname = null; } $savemessage->timecreated = time(); if (PHPUNIT_TEST and class_exists('phpunit_util')) { // Add some more tests to make sure the normal code can actually work. $componentdir = core_component::get_component_directory($eventdata->component); if (!$componentdir or !is_dir($componentdir)) { throw new coding_exception('Invalid component specified in message-send(): ' . $eventdata->component); } if (!file_exists("{$componentdir}/db/messages.php")) { throw new coding_exception("{$eventdata->component} does not contain db/messages.php necessary for message_send()"); } $messageproviders = null; include "{$componentdir}/db/messages.php"; if (!isset($messageproviders[$eventdata->name])) { throw new coding_exception("Missing messaging defaults for event '{$eventdata->name}' in '{$eventdata->component}' messages.php file"); } unset($componentdir); unset($messageproviders); // Now ask phpunit if it wants to catch this message. if (phpunit_util::is_redirecting_messages()) { $savemessage->timeread = time(); $messageid = $DB->insert_record('message_read', $savemessage); $message = $DB->get_record('message_read', array('id' => $messageid)); phpunit_util::message_sent($message); return $messageid; } } // Fetch enabled processors $processors = get_message_processors(true); // Preset variables $processorlist = array(); // Fill in the array of processors to be used based on default and user preferences foreach ($processors as $processor) { // Skip adding processors for internal user, if processor doesn't support sending message to internal user. if (!$usertoisrealuser && !$processor->object->can_send_to_any_users()) { continue; } // First find out permissions $defaultpreference = $processor->name . '_provider_' . $preferencebase . '_permitted'; if (isset($defaultpreferences->{$defaultpreference})) { $permitted = $defaultpreferences->{$defaultpreference}; } else { // MDL-25114 They supplied an $eventdata->component $eventdata->name combination which doesn't // exist in the message_provider table (thus there is no default settings for them). $preferrormsg = "Could not load preference {$defaultpreference}. Make sure the component and name you supplied\n to message_send() are valid."; throw new coding_exception($preferrormsg); } // Find out if user has configured this output // Some processors cannot function without settings from the user $userisconfigured = $processor->object->is_user_configured($eventdata->userto); // DEBUG: notify if we are forcing unconfigured output if ($permitted == 'forced' && !$userisconfigured) { debugging('Attempt to force message delivery to user who has "' . $processor->name . '" output unconfigured', DEBUG_NORMAL); } // Warn developers that necessary data is missing regardless of how the processors are configured if (!isset($eventdata->userto->emailstop)) { debugging('userto->emailstop is not set. Retrieving it from the user table'); $eventdata->userto->emailstop = $DB->get_field('user', 'emailstop', array('id' => $eventdata->userto->id)); } // Populate the list of processors we will be using if ($permitted == 'forced' && $userisconfigured) { // An admin is forcing users to use this message processor. Use this processor unconditionally. $processorlist[] = $processor->name; } else { if ($permitted == 'permitted' && $userisconfigured && !$eventdata->userto->emailstop) { // User has not disabled notifications // See if user set any notification preferences, otherwise use site default ones $userpreferencename = 'message_provider_' . $preferencebase . '_' . $userstate; if ($userpreference = get_user_preferences($userpreferencename, null, $eventdata->userto->id)) { if (in_array($processor->name, explode(',', $userpreference))) { $processorlist[] = $processor->name; } } else { if (isset($defaultpreferences->{$userpreferencename})) { if (in_array($processor->name, explode(',', $defaultpreferences->{$userpreferencename}))) { $processorlist[] = $processor->name; } } } } } } if (empty($processorlist) && $savemessage->notification) { //if they have deselected all processors and its a notification mark it read. The user doesnt want to be bothered $savemessage->timeread = time(); $messageid = $DB->insert_record('message_read', $savemessage); } else { // Process the message // Store unread message just in case we can not send it $messageid = $savemessage->id = $DB->insert_record('message', $savemessage); $eventdata->savedmessageid = $savemessage->id; // Try to deliver the message to each processor if (!empty($processorlist)) { foreach ($processorlist as $procname) { if (!$processors[$procname]->object->send_message($eventdata)) { debugging('Error calling message processor ' . $procname); $messageid = false; } } //if messaging is disabled and they previously had forum notifications handled by the popup processor //or any processor that puts a row in message_working then the notification will remain forever //unread. To prevent this mark the message read if messaging is disabled if (empty($CFG->messaging)) { require_once $CFG->dirroot . '/message/lib.php'; $messageid = message_mark_message_read($savemessage, time()); } else { if ($DB->count_records('message_working', array('unreadmessageid' => $savemessage->id)) == 0) { //if there is no more processors that want to process this we can move message to message_read require_once $CFG->dirroot . '/message/lib.php'; $messageid = message_mark_message_read($savemessage, time(), true); } } } } // We may be sending a message from the 'noreply' address, which means we are not actually sending a // message from a valid user. In this case, we will set the userid to 0. // Check if the userid is valid. if (core_user::is_real_user($eventdata->userfrom->id)) { $userfromid = $eventdata->userfrom->id; } else { $userfromid = 0; } // Trigger event for sending a message. $event = \core\event\message_sent::create(array('userid' => $userfromid, 'context' => context_system::instance(), 'relateduserid' => $eventdata->userto->id, 'other' => array('messageid' => $messageid))); $event->trigger(); return $messageid; }
/** * Message someone about something. * * @param stdClass $userfrom * @param stdClass $userto * @param string $messagetype * @param string $eventtype * @param int $updatetime * @return void */ public function send_notification($userfrom, $userto, $messagetype, $eventtype, $updatetime) { global $USER; $userid = core_user::is_real_user($userfrom->id) ? $userfrom->id : $USER->id; $uniqueid = $this->get_uniqueid_for_user($userid); self::send_assignment_notification($userfrom, $userto, $messagetype, $eventtype, $updatetime, $this->get_course_module(), $this->get_context(), $this->get_course(), $this->get_module_name(), $this->get_instance()->name, $this->is_blind_marking(), $uniqueid); }
/** * Return legacy data for add_to_log(). * * @return array */ protected function get_legacy_logdata() { // The add_to_log function was only ever called when we sent a message from one user to another. We do not want // to return the legacy log data if we are sending a system message, so check that the userid is valid. if (\core_user::is_real_user($this->userid)) { return array(SITEID, 'message', 'write', 'index.php?user='******'&id=' . $this->relateduserid . '&history=1#m' . $this->other['messageid'], $this->userid); } return null; }
/** * Validate the action user ID. * * @param int $value A user ID. * @return true|lang_string */ protected function validate_actionuserid($value) { if ($value !== null && !\core_user::is_real_user($value)) { return new lang_string('invaliddata', 'error'); } return true; }
/** * Mark all notifications as read function. * * @since 3.2 * @throws invalid_parameter_exception * @throws moodle_exception * @param int $useridto the user id who received the message * @param int $useridfrom the user id who send the message. -10 or -20 for no-reply or support user * @return external_description */ public static function mark_all_messages_as_read($useridto, $useridfrom) { global $USER, $CFG; // Check if messaging is enabled. if (empty($CFG->messaging)) { throw new moodle_exception('disabled', 'message'); } $params = self::validate_parameters(self::mark_all_messages_as_read_parameters(), array('useridto' => $useridto, 'useridfrom' => $useridfrom)); $context = context_system::instance(); self::validate_context($context); $useridto = $params['useridto']; $useridfrom = $params['useridfrom']; if (!empty($useridto)) { if (core_user::is_real_user($useridto)) { $userto = core_user::get_user($useridto, '*', MUST_EXIST); } else { throw new moodle_exception('invaliduser'); } } if (!empty($useridfrom)) { // We use get_user here because the from user can be the noreply or support user. $userfrom = core_user::get_user($useridfrom, '*', MUST_EXIST); } // Check if the current user is the sender/receiver or just a privileged user. if ($useridto != $USER->id and $useridfrom != $USER->id and !has_capability('moodle/site:deleteanymessage', $context)) { throw new moodle_exception('accessdenied', 'admin'); } \core_message\api::mark_all_read_for_user($useridto, $useridfrom, MESSAGE_TYPE_MESSAGE); return true; }
/** * Print information on a user. Used when printing search results. * * @param object/bool $user the user to display or false if you just want $USER * @param bool $iscontact is the user being displayed a contact? * @param bool $isblocked is the user being displayed blocked? * @param bool $includeicontext include text next to the action icons? * @return void */ function message_print_user($user = false, $iscontact = false, $isblocked = false, $includeicontext = false) { global $USER, $OUTPUT; $userpictureparams = array('size' => 20, 'courseid' => SITEID); if ($user === false) { echo $OUTPUT->user_picture($USER, $userpictureparams); } else { if (core_user::is_real_user($user->id)) { // If not real user, then don't show any links. $userpictureparams['link'] = false; echo $OUTPUT->user_picture($USER, $userpictureparams); echo fullname($user); } else { echo $OUTPUT->user_picture($user, $userpictureparams); $link = new moodle_url("/message/index.php?id={$user->id}"); echo $OUTPUT->action_link($link, fullname($user), null, array('title' => get_string('sendmessageto', 'message', fullname($user)))); $return = false; $script = null; if ($iscontact) { message_contact_link($user->id, 'remove', $return, $script, $includeicontext); } else { message_contact_link($user->id, 'add', $return, $script, $includeicontext); } if ($isblocked) { message_contact_link($user->id, 'unblock', $return, $script, $includeicontext); } else { message_contact_link($user->id, 'block', $return, $script, $includeicontext); } } } }
/** * Get unread notification count function. * * @since 3.2 * @throws invalid_parameter_exception * @throws moodle_exception * @param int $useridto the user id who received the message * @return external_description */ public static function get_unread_popup_notification_count($useridto) { global $USER; $params = self::validate_parameters(self::get_unread_popup_notification_count_parameters(), array('useridto' => $useridto)); $context = context_system::instance(); self::validate_context($context); $useridto = $params['useridto']; if (!empty($useridto)) { if (core_user::is_real_user($useridto)) { $userto = core_user::get_user($useridto, '*', MUST_EXIST); } else { throw new moodle_exception('invaliduser'); } } // Check if the current user is the sender/receiver or just a privileged user. if ($useridto != $USER->id and !has_capability('moodle/site:readallmessages', $context)) { throw new moodle_exception('accessdenied', 'admin'); } return \message_popup\api::count_unread_popup_notifications($useridto); }