mirror of
https://github.com/moodle/moodle.git
synced 2025-01-19 06:18:28 +01:00
MDL-61919 core_message: implement privacy provider
This commit is contained in:
parent
446d8483a3
commit
04cd1b3f31
@ -99,6 +99,44 @@ $string['outputenabled'] = 'Output enabled';
|
||||
$string['outputnotavailable'] = 'Not available';
|
||||
$string['outputnotconfigured'] = 'Not configured';
|
||||
$string['permitted'] = 'Permitted';
|
||||
$string['privacy:metadata:messages'] = 'Messages';
|
||||
$string['privacy:metadata:messages:conversationid'] = 'The ID of the conversation';
|
||||
$string['privacy:metadata:messages:fullmessage'] = 'The full message';
|
||||
$string['privacy:metadata:messages:fullmessageformat'] = 'The format of the full message';
|
||||
$string['privacy:metadata:messages:fullmessagehtml'] = 'The HTML format of the full message';
|
||||
$string['privacy:metadata:messages:useridfrom'] = 'The ID of the user who sent the message';
|
||||
$string['privacy:metadata:messages:smallmessage'] = 'A small version of the message';
|
||||
$string['privacy:metadata:messages:subject'] = 'The subject of the message';
|
||||
$string['privacy:metadata:messages:timecreated'] = 'The date at which the message was created';
|
||||
$string['privacy:metadata:message_contacts'] = 'The list of contacts';
|
||||
$string['privacy:metadata:message_contacts:blocked'] = 'Flag whether or not the user is blocked';
|
||||
$string['privacy:metadata:message_contacts:contactid'] = 'The ID of the user who is a contact';
|
||||
$string['privacy:metadata:message_contacts:userid'] = 'The ID of the user whose contact list we are viewing';
|
||||
$string['privacy:metadata:message_conversation_members'] = 'The list of users in a conversation';
|
||||
$string['privacy:metadata:message_conversation_members:conversationid'] = 'The ID of the conversation';
|
||||
$string['privacy:metadata:message_conversation_members:timecreated'] = 'The date at which the member was created';
|
||||
$string['privacy:metadata:message_conversation_members:userid'] = 'The ID of the user in a conversation';
|
||||
$string['privacy:metadata:message_user_actions'] = 'The list of message user actions';
|
||||
$string['privacy:metadata:message_user_actions:action'] = 'The action that was performed';
|
||||
$string['privacy:metadata:message_user_actions:messageid'] = 'The ID of the message this action belongs to';
|
||||
$string['privacy:metadata:message_user_actions:timecreated'] = 'The date at which the action was created';
|
||||
$string['privacy:metadata:message_user_actions:userid'] = 'The ID of the user who performed this action';
|
||||
$string['privacy:metadata:notifications'] = 'Notifications';
|
||||
$string['privacy:metadata:notifications:component'] = 'The component responsible for sending the notification';
|
||||
$string['privacy:metadata:notifications:contexturl'] = 'The URL related to this notification';
|
||||
$string['privacy:metadata:notifications:contexturlname'] = 'The name of the context';
|
||||
$string['privacy:metadata:notifications:eventtype'] = 'The event type';
|
||||
$string['privacy:metadata:notifications:fullmessage'] = 'The full notification';
|
||||
$string['privacy:metadata:notifications:fullmessageformat'] = 'The notification format';
|
||||
$string['privacy:metadata:notifications:fullmessagehtml'] = 'The HTML of the notification';
|
||||
$string['privacy:metadata:notifications:smallmessage'] = 'The small message of the notification';
|
||||
$string['privacy:metadata:notifications:subject'] = 'The subject of the notification';
|
||||
$string['privacy:metadata:notifications:timeread'] = 'The date at which the notification was read';
|
||||
$string['privacy:metadata:notifications:timecreated'] = 'The date at which the notification was created';
|
||||
$string['privacy:metadata:notifications:useridfrom'] = 'The ID of the user who sent the notification';
|
||||
$string['privacy:metadata:notifications:useridto'] = 'The ID of the user who received the notification';
|
||||
$string['privacy:metadata:preference:core_message_settings'] = 'Settings related to messaging';
|
||||
$string['privacy:request:preference:set'] = 'The value of the setting \'{$a->name}\' was \'{$a->value}\'';
|
||||
$string['processorsettings'] = 'Processor settings';
|
||||
$string['removecontact'] = 'Remove contact';
|
||||
$string['removecoursefilter'] = 'Remove filter for course {$a}';
|
||||
@ -130,6 +168,7 @@ $string['togglenotificationmenu'] = 'Toggle notifications menu';
|
||||
$string['togglemessagemenu'] = 'Toggle messages menu';
|
||||
$string['touserdoesntexist'] = 'You can not send a message to a user id ({$a}) that doesn\'t exist';
|
||||
$string['unblockcontact'] = 'Unblock contact';
|
||||
$string['unknownuser'] = 'Unknown user';
|
||||
$string['unreadnotification'] = 'Unread notification: {$a}';
|
||||
$string['unreadnewmessage'] = 'New message from {$a}';
|
||||
$string['userisblockingyou'] = 'This user has blocked you from sending messages to them';
|
||||
|
374
message/classes/privacy/provider.php
Normal file
374
message/classes/privacy/provider.php
Normal file
@ -0,0 +1,374 @@
|
||||
<?php
|
||||
// This file is part of Moodle - http://moodle.org/
|
||||
//
|
||||
// Moodle is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// Moodle is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with Moodle. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
/**
|
||||
* Privacy Subsystem implementation for core_message.
|
||||
*
|
||||
* @package core_message
|
||||
* @copyright 2018 Mark Nelson <markn@moodle.com>
|
||||
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
|
||||
*/
|
||||
namespace core_message\privacy;
|
||||
|
||||
use core_privacy\local\metadata\collection;
|
||||
use core_privacy\local\request\approved_contextlist;
|
||||
use core_privacy\local\request\contextlist;
|
||||
use core_privacy\local\request\transform;
|
||||
use core_privacy\local\request\writer;
|
||||
|
||||
defined('MOODLE_INTERNAL') || die();
|
||||
|
||||
/**
|
||||
* Privacy Subsystem implementation for core_message.
|
||||
*
|
||||
* @copyright 2018 Mark Nelson <markn@moodle.com>
|
||||
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
|
||||
*/
|
||||
class provider implements
|
||||
\core_privacy\local\metadata\provider,
|
||||
\core_privacy\local\request\subsystem\provider,
|
||||
\core_privacy\local\request\user_preference_provider {
|
||||
|
||||
/**
|
||||
* Return the fields which contain personal data.
|
||||
*
|
||||
* @param collection $items a reference to the collection to use to store the metadata.
|
||||
* @return collection the updated collection of metadata items.
|
||||
*/
|
||||
public static function get_metadata(collection $items) : collection {
|
||||
$items->add_database_table(
|
||||
'messages',
|
||||
[
|
||||
'useridfrom' => 'privacy:metadata:messages:useridfrom',
|
||||
'conversationid' => 'privacy:metadata:messages:conversationid',
|
||||
'subject' => 'privacy:metadata:messages:subject',
|
||||
'fullmessage' => 'privacy:metadata:messages:fullmessage',
|
||||
'fullmessageformat' => 'privacy:metadata:messages:fullmessageformat',
|
||||
'fullmessagehtml' => 'privacy:metadata:messages:fullmessagehtml',
|
||||
'smallmessage' => 'privacy:metadata:messages:smallmessage',
|
||||
'timecreated' => 'privacy:metadata:messages:timecreated'
|
||||
],
|
||||
'privacy:metadata:messages'
|
||||
);
|
||||
|
||||
$items->add_database_table(
|
||||
'message_user_actions',
|
||||
[
|
||||
'userid' => 'privacy:metadata:message_user_actions:userid',
|
||||
'messageid' => 'privacy:metadata:message_user_actions:messageid',
|
||||
'action' => 'privacy:metadata:message_user_actions:action',
|
||||
'timecreated' => 'privacy:metadata:message_user_actions:timecreated'
|
||||
],
|
||||
'privacy:metadata:message_user_actions'
|
||||
);
|
||||
|
||||
$items->add_database_table(
|
||||
'message_conversation_members',
|
||||
[
|
||||
'conversationid' => 'privacy:metadata:message_conversation_members:conversationid',
|
||||
'userid' => 'privacy:metadata:message_conversation_members:userid',
|
||||
'timecreated' => 'privacy:metadata:message_conversation_members:timecreated',
|
||||
],
|
||||
'privacy:metadata:message_conversation_members'
|
||||
);
|
||||
|
||||
$items->add_database_table(
|
||||
'message_contacts',
|
||||
[
|
||||
'userid' => 'privacy:metadata:message_contacts:userid',
|
||||
'contactid' => 'privacy:metadata:message_contacts:contactid',
|
||||
'blocked' => 'privacy:metadata:message_contacts:blocked',
|
||||
],
|
||||
'privacy:metadata:message_contacts'
|
||||
);
|
||||
|
||||
$items->add_database_table(
|
||||
'notifications',
|
||||
[
|
||||
'useridfrom' => 'privacy:metadata:notifications:useridfrom',
|
||||
'useridto' => 'privacy:metadata:notifications:useridto',
|
||||
'subject' => 'privacy:metadata:notifications:subject',
|
||||
'fullmessage' => 'privacy:metadata:notifications:fullmessage',
|
||||
'fullmessageformat' => 'privacy:metadata:notifications:fullmessageformat',
|
||||
'fullmessagehtml' => 'privacy:metadata:notifications:fullmessagehtml',
|
||||
'smallmessage' => 'privacy:metadata:notifications:smallmessage',
|
||||
'component' => 'privacy:metadata:notifications:component',
|
||||
'eventtype' => 'privacy:metadata:notifications:eventtype',
|
||||
'contexturl' => 'privacy:metadata:notifications:contexturl',
|
||||
'contexturlname' => 'privacy:metadata:notifications:contexturlname',
|
||||
'timeread' => 'privacy:metadata:notifications:timeread',
|
||||
'timecreated' => 'privacy:metadata:notifications:timecreated',
|
||||
],
|
||||
'privacy:metadata:notifications'
|
||||
);
|
||||
|
||||
// Note - we are not adding the 'message' and 'message_read' tables
|
||||
// as they are legacy tables. This information is moved to these
|
||||
// new tables in a separate ad-hoc task. See MDL-61255.
|
||||
|
||||
// Now add that we also have user preferences.
|
||||
$items->add_user_preference('core_message_messageprovider_settings',
|
||||
'privacy:metadata:preference:core_message_settings');
|
||||
|
||||
return $items;
|
||||
}
|
||||
|
||||
/**
|
||||
* Store all user preferences for core message.
|
||||
*
|
||||
* @param int $userid The userid of the user whose data is to be exported.
|
||||
*/
|
||||
public static function export_user_preferences(int $userid) {
|
||||
$preferences = get_user_preferences(null, null, $userid);
|
||||
foreach ($preferences as $name => $value) {
|
||||
if ((substr($name, 0, 16) == 'message_provider') || ($name == 'message_blocknoncontacts')) {
|
||||
writer::export_user_preference(
|
||||
'core_message',
|
||||
$name,
|
||||
$value,
|
||||
get_string('privacy:request:preference:set', 'core_message', (object) [
|
||||
'name' => $name,
|
||||
'value' => $value,
|
||||
])
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the list of contexts that contain user information for the specified user.
|
||||
*
|
||||
* @param int $userid the userid.
|
||||
* @return contextlist the list of contexts containing user info for the user.
|
||||
*/
|
||||
public static function get_contexts_for_userid(int $userid) : contextlist {
|
||||
// Messages are in the system context.
|
||||
$contextlist = new contextlist();
|
||||
$contextlist->add_system_context();
|
||||
|
||||
return $contextlist;
|
||||
}
|
||||
|
||||
/**
|
||||
* Export personal data for the given approved_contextlist. User and context information is contained within the contextlist.
|
||||
*
|
||||
* @param approved_contextlist $contextlist a list of contexts approved for export.
|
||||
*/
|
||||
public static function export_user_data(approved_contextlist $contextlist) {
|
||||
if (empty($contextlist->count())) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Remove non-system contexts. If it ends up empty then early return.
|
||||
$contexts = array_filter($contextlist->get_contexts(), function($context) {
|
||||
return $context->contextlevel == CONTEXT_SYSTEM;
|
||||
});
|
||||
|
||||
if (empty($contexts)) {
|
||||
return;
|
||||
}
|
||||
|
||||
$userid = $contextlist->get_user()->id;
|
||||
|
||||
// Export the contacts.
|
||||
self::export_user_data_contacts($userid);
|
||||
|
||||
// Export the notifications.
|
||||
self::export_user_data_notifications($userid);
|
||||
|
||||
// Export the messages, with any related actions.
|
||||
self::export_user_data_messages($userid);
|
||||
}
|
||||
|
||||
/**
|
||||
* Delete all data for all users in the specified context.
|
||||
*
|
||||
* @param \context $context the context to delete in.
|
||||
*/
|
||||
public static function delete_data_for_all_users_in_context(\context $context) {
|
||||
global $DB;
|
||||
|
||||
if (!$context instanceof \context_system) {
|
||||
return;
|
||||
}
|
||||
|
||||
$DB->delete_records('messages');
|
||||
$DB->delete_records('message_user_actions');
|
||||
$DB->delete_records('message_conversation_members');
|
||||
$DB->delete_records('message_contacts');
|
||||
$DB->delete_records('notifications');
|
||||
}
|
||||
|
||||
/**
|
||||
* Delete all user data for the specified user, in the specified contexts.
|
||||
*
|
||||
* @param approved_contextlist $contextlist a list of contexts approved for deletion.
|
||||
*/
|
||||
public static function delete_data_for_user(approved_contextlist $contextlist) {
|
||||
global $DB;
|
||||
|
||||
if (empty($contextlist->count())) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Remove non-system contexts. If it ends up empty then early return.
|
||||
$contexts = array_filter($contextlist->get_contexts(), function($context) {
|
||||
return $context->contextlevel == CONTEXT_SYSTEM;
|
||||
});
|
||||
|
||||
if (empty($contexts)) {
|
||||
return;
|
||||
}
|
||||
|
||||
$userid = $contextlist->get_user()->id;
|
||||
|
||||
$DB->delete_records('messages', ['useridfrom' => $userid]);
|
||||
$DB->delete_records('message_user_actions', ['userid' => $userid]);
|
||||
$DB->delete_records('message_conversation_members', ['userid' => $userid]);
|
||||
$DB->delete_records_select('message_contacts', 'userid = ? OR contactid = ?', [$userid, $userid]);
|
||||
$DB->delete_records_select('notifications', 'useridfrom = ? OR useridto = ?', [$userid, $userid]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Export the messaging contact data.
|
||||
*
|
||||
* @param int $userid
|
||||
*/
|
||||
protected static function export_user_data_contacts(int $userid) {
|
||||
global $DB;
|
||||
|
||||
$context = \context_system::instance();
|
||||
|
||||
// Get the user's contacts.
|
||||
if ($contacts = $DB->get_records('message_contacts', ['userid' => $userid], 'id ASC')) {
|
||||
$contactdata = [];
|
||||
foreach ($contacts as $contact) {
|
||||
$contactdata[] = (object) [
|
||||
'contact' => transform::user($contact->contactid),
|
||||
'blocked' => transform::yesno($contact->blocked)
|
||||
];
|
||||
}
|
||||
writer::with_context($context)->export_data([get_string('contacts', 'core_message')], (object) $contactdata);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Export the messaging data.
|
||||
*
|
||||
* @param int $userid
|
||||
*/
|
||||
protected static function export_user_data_messages(int $userid) {
|
||||
global $DB;
|
||||
|
||||
$context = \context_system::instance();
|
||||
|
||||
$sql = "SELECT DISTINCT mcm.conversationid as id
|
||||
FROM {message_conversation_members} mcm
|
||||
WHERE mcm.userid = :userid";
|
||||
if ($conversations = $DB->get_records_sql($sql, ['userid' => $userid])) {
|
||||
// Ok, let's get the other users in the conversations.
|
||||
$conversationids = array_keys($conversations);
|
||||
list($conversationidsql, $conversationparams) = $DB->get_in_or_equal($conversationids, SQL_PARAMS_NAMED);
|
||||
$userfields = \user_picture::fields('u');
|
||||
$userssql = "SELECT mcm.conversationid, $userfields
|
||||
FROM {user} u
|
||||
INNER JOIN {message_conversation_members} mcm
|
||||
ON u.id = mcm.userid
|
||||
WHERE mcm.conversationid $conversationidsql
|
||||
AND mcm.userid != :userid
|
||||
AND u.deleted = 0";
|
||||
$otherusers = $DB->get_records_sql($userssql, $conversationparams + ['userid' => $userid]);
|
||||
foreach ($conversations as $conversation) {
|
||||
$otheruserfullname = get_string('unknownuser', 'core_message');
|
||||
|
||||
// It's possible the other user has requested to be deleted, so might not exist
|
||||
// as a conversation member, or they have just been deleted.
|
||||
if (isset($otherusers[$conversation->id])) {
|
||||
$otheruserfullname = fullname($otherusers[$conversation->id]);
|
||||
}
|
||||
|
||||
// Get all the messages for this conversation from start to finish.
|
||||
$sql = "SELECT m.*, muadelete.timecreated as timedeleted, muaread.timecreated as timeread
|
||||
FROM {messages} m
|
||||
LEFT JOIN {message_user_actions} muadelete
|
||||
ON m.id = muadelete.messageid AND muadelete.action = :deleteaction
|
||||
LEFT JOIN {message_user_actions} muaread
|
||||
ON m.id = muaread.messageid AND muaread.action = :readaction
|
||||
WHERE conversationid = :conversationid
|
||||
ORDER BY m.timecreated ASC";
|
||||
$messages = $DB->get_recordset_sql($sql, ['deleteaction' => \core_message\api::MESSAGE_ACTION_DELETED,
|
||||
'readaction' => \core_message\api::MESSAGE_ACTION_READ, 'conversationid' => $conversation->id]);
|
||||
$messagedata = [];
|
||||
foreach ($messages as $message) {
|
||||
$timeread = !is_null($message->timeread) ? transform::datetime($message->timeread) : '-';
|
||||
$issender = $userid == $message->useridfrom;
|
||||
|
||||
$data = [
|
||||
'sender' => transform::yesno($issender),
|
||||
'message' => message_format_message_text($message),
|
||||
'timecreated' => transform::datetime($message->timecreated),
|
||||
'timeread' => $timeread
|
||||
];
|
||||
|
||||
if (!is_null($message->timedeleted)) {
|
||||
$data['timedeleted'] = transform::datetime($message->timedeleted);
|
||||
}
|
||||
|
||||
$messagedata[] = (object) $data;
|
||||
}
|
||||
$messages->close();
|
||||
|
||||
writer::with_context($context)->export_data([get_string('messages', 'core_message'), $otheruserfullname],
|
||||
(object) $messagedata);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Export the notification data.
|
||||
*
|
||||
* @param int $userid
|
||||
*/
|
||||
protected static function export_user_data_notifications(int $userid) {
|
||||
global $DB;
|
||||
|
||||
$context = \context_system::instance();
|
||||
|
||||
$notificationdata = [];
|
||||
$select = "useridfrom = ? OR useridto = ?";
|
||||
$notifications = $DB->get_recordset_select('notifications', $select, [$userid, $userid], 'timecreated ASC');
|
||||
foreach ($notifications as $notification) {
|
||||
$timeread = !is_null($notification->timeread) ? transform::datetime($notification->timeread) : '-';
|
||||
|
||||
$data = (object) [
|
||||
'subject' => $notification->subject,
|
||||
'fullmessage' => $notification->fullmessage,
|
||||
'smallmessage' => $notification->smallmessage,
|
||||
'component' => $notification->component,
|
||||
'eventtype' => $notification->eventtype,
|
||||
'contexturl' => $notification->contexturl,
|
||||
'contexturlname' => $notification->contexturlname,
|
||||
'timeread' => $timeread,
|
||||
'timecreated' => transform::datetime($notification->timecreated)
|
||||
];
|
||||
|
||||
$notificationdata[] = $data;
|
||||
}
|
||||
$notifications->close();
|
||||
|
||||
writer::with_context($context)->export_data([get_string('notifications', 'core_message')], (object) $notificationdata);
|
||||
}
|
||||
}
|
587
message/tests/privacy_provider_test.php
Normal file
587
message/tests/privacy_provider_test.php
Normal file
@ -0,0 +1,587 @@
|
||||
<?php
|
||||
// This file is part of Moodle - http://moodle.org/
|
||||
//
|
||||
// Moodle is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// Moodle is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with Moodle. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
/**
|
||||
* Privacy provider tests.
|
||||
*
|
||||
* @package core_message
|
||||
* @copyright 2018 Mark Nelson <markn@moodle.com>
|
||||
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
|
||||
*/
|
||||
|
||||
use core_privacy\local\metadata\collection;
|
||||
use core_message\privacy\provider;
|
||||
use \core_privacy\local\request\writer;
|
||||
use \core_privacy\local\request\transform;
|
||||
|
||||
defined('MOODLE_INTERNAL') || die();
|
||||
|
||||
/**
|
||||
* Privacy provider tests class.
|
||||
*
|
||||
* @package core_message
|
||||
* @copyright 2018 Mark Nelson <markn@moodle.com>
|
||||
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
|
||||
*/
|
||||
class core_message_privacy_provider_testcase extends \core_privacy\tests\provider_testcase {
|
||||
|
||||
/**
|
||||
* Test for provider::get_metadata().
|
||||
*/
|
||||
public function test_get_metadata() {
|
||||
$collection = new collection('core_message');
|
||||
$newcollection = provider::get_metadata($collection);
|
||||
$itemcollection = $newcollection->get_collection();
|
||||
$this->assertCount(6, $itemcollection);
|
||||
|
||||
$messagestable = array_shift($itemcollection);
|
||||
$this->assertEquals('messages', $messagestable->get_name());
|
||||
|
||||
$messageuseractionstable = array_shift($itemcollection);
|
||||
$this->assertEquals('message_user_actions', $messageuseractionstable->get_name());
|
||||
|
||||
$messageconversationmemberstable = array_shift($itemcollection);
|
||||
$this->assertEquals('message_conversation_members', $messageconversationmemberstable->get_name());
|
||||
|
||||
$messagecontacts = array_shift($itemcollection);
|
||||
$this->assertEquals('message_contacts', $messagecontacts->get_name());
|
||||
|
||||
$notificationstable = array_shift($itemcollection);
|
||||
$this->assertEquals('notifications', $notificationstable->get_name());
|
||||
|
||||
$usersettings = array_shift($itemcollection);
|
||||
$this->assertEquals('core_message_messageprovider_settings', $usersettings->get_name());
|
||||
|
||||
$privacyfields = $messagestable->get_privacy_fields();
|
||||
$this->assertArrayHasKey('useridfrom', $privacyfields);
|
||||
$this->assertArrayHasKey('conversationid', $privacyfields);
|
||||
$this->assertArrayHasKey('subject', $privacyfields);
|
||||
$this->assertArrayHasKey('fullmessage', $privacyfields);
|
||||
$this->assertArrayHasKey('fullmessageformat', $privacyfields);
|
||||
$this->assertArrayHasKey('fullmessagehtml', $privacyfields);
|
||||
$this->assertArrayHasKey('smallmessage', $privacyfields);
|
||||
$this->assertArrayHasKey('timecreated', $privacyfields);
|
||||
$this->assertEquals('privacy:metadata:messages', $messagestable->get_summary());
|
||||
|
||||
$privacyfields = $messageuseractionstable->get_privacy_fields();
|
||||
$this->assertArrayHasKey('userid', $privacyfields);
|
||||
$this->assertArrayHasKey('messageid', $privacyfields);
|
||||
$this->assertArrayHasKey('action', $privacyfields);
|
||||
$this->assertArrayHasKey('timecreated', $privacyfields);
|
||||
$this->assertEquals('privacy:metadata:message_user_actions', $messageuseractionstable->get_summary());
|
||||
|
||||
$privacyfields = $messageconversationmemberstable->get_privacy_fields();
|
||||
$this->assertArrayHasKey('conversationid', $privacyfields);
|
||||
$this->assertArrayHasKey('userid', $privacyfields);
|
||||
$this->assertArrayHasKey('timecreated', $privacyfields);
|
||||
$this->assertEquals('privacy:metadata:message_conversation_members', $messageconversationmemberstable->get_summary());
|
||||
|
||||
$privacyfields = $messagecontacts->get_privacy_fields();
|
||||
$this->assertArrayHasKey('userid', $privacyfields);
|
||||
$this->assertArrayHasKey('contactid', $privacyfields);
|
||||
$this->assertArrayHasKey('blocked', $privacyfields);
|
||||
$this->assertEquals('privacy:metadata:message_contacts', $messagecontacts->get_summary());
|
||||
|
||||
$privacyfields = $notificationstable->get_privacy_fields();
|
||||
$this->assertArrayHasKey('useridfrom', $privacyfields);
|
||||
$this->assertArrayHasKey('useridto', $privacyfields);
|
||||
$this->assertArrayHasKey('subject', $privacyfields);
|
||||
$this->assertArrayHasKey('fullmessage', $privacyfields);
|
||||
$this->assertArrayHasKey('fullmessageformat', $privacyfields);
|
||||
$this->assertArrayHasKey('fullmessagehtml', $privacyfields);
|
||||
$this->assertArrayHasKey('smallmessage', $privacyfields);
|
||||
$this->assertArrayHasKey('component', $privacyfields);
|
||||
$this->assertArrayHasKey('eventtype', $privacyfields);
|
||||
$this->assertArrayHasKey('contexturl', $privacyfields);
|
||||
$this->assertArrayHasKey('contexturlname', $privacyfields);
|
||||
$this->assertArrayHasKey('timeread', $privacyfields);
|
||||
$this->assertArrayHasKey('timecreated', $privacyfields);
|
||||
$this->assertEquals('privacy:metadata:notifications', $notificationstable->get_summary());
|
||||
}
|
||||
|
||||
/**
|
||||
* Test for provider::export_user_preferences().
|
||||
*/
|
||||
public function test_export_user_preferences_no_pref() {
|
||||
$this->resetAfterTest();
|
||||
|
||||
$user = $this->getDataGenerator()->create_user();
|
||||
provider::export_user_preferences($user->id);
|
||||
|
||||
$writer = writer::with_context(\context_system::instance());
|
||||
|
||||
$this->assertFalse($writer->has_any_data());
|
||||
}
|
||||
|
||||
/**
|
||||
* Test for provider::export_user_preferences().
|
||||
*/
|
||||
public function test_export_user_preferences() {
|
||||
global $USER;
|
||||
|
||||
$this->resetAfterTest();
|
||||
|
||||
$this->setAdminUser();
|
||||
|
||||
// Create another user to set a preference for who we won't be exporting.
|
||||
$user = $this->getDataGenerator()->create_user();
|
||||
|
||||
// Set some message user preferences.
|
||||
set_user_preference('message_provider_moodle_instantmessage_loggedin', 'airnotifier', $USER->id);
|
||||
set_user_preference('message_provider_moodle_instantmessage_loggedoff', 'popup', $USER->id);
|
||||
set_user_preference('message_blocknoncontacts', 1, $USER->id);
|
||||
set_user_preference('message_provider_moodle_instantmessage_loggedoff', 'inbound', $user->id);
|
||||
|
||||
// Set an unrelated preference.
|
||||
set_user_preference('block_myoverview_last_tab', 'courses', $USER->id);
|
||||
|
||||
provider::export_user_preferences($USER->id);
|
||||
|
||||
$writer = writer::with_context(\context_system::instance());
|
||||
|
||||
$this->assertTrue($writer->has_any_data());
|
||||
|
||||
$prefs = (array) $writer->get_user_preferences('core_message');
|
||||
|
||||
// Check only 3 preferences exist.
|
||||
$this->assertCount(3, $prefs);
|
||||
$this->assertArrayHasKey('message_provider_moodle_instantmessage_loggedin', $prefs);
|
||||
$this->assertArrayHasKey('message_provider_moodle_instantmessage_loggedoff', $prefs);
|
||||
$this->assertArrayHasKey('message_blocknoncontacts', $prefs);
|
||||
|
||||
foreach ($prefs as $key => $pref) {
|
||||
if ($key == 'message_provider_moodle_instantmessage_loggedin') {
|
||||
$this->assertEquals('airnotifier', $pref->value);
|
||||
} else if ($key == 'message_provider_moodle_instantmessage_loggedoff') {
|
||||
$this->assertEquals('popup', $pref->value);
|
||||
} else {
|
||||
$this->assertEquals(1, $pref->value);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Test for provider::get_contexts_for_userid().
|
||||
*/
|
||||
public function test_get_contexts_for_userid() {
|
||||
$this->resetAfterTest();
|
||||
|
||||
$user = $this->getDataGenerator()->create_user();
|
||||
$contextlist = provider::get_contexts_for_userid($user->id);
|
||||
$this->assertCount(1, $contextlist);
|
||||
$contextforuser = $contextlist->current();
|
||||
$this->assertEquals(SYSCONTEXTID, $contextforuser->id);
|
||||
}
|
||||
|
||||
/**
|
||||
* Test for provider::export_user_data().
|
||||
*/
|
||||
public function test_export_for_context_with_contacts() {
|
||||
$this->resetAfterTest();
|
||||
|
||||
// Create users to test with.
|
||||
$user1 = $this->getDataGenerator()->create_user();
|
||||
$user2 = $this->getDataGenerator()->create_user();
|
||||
$user3 = $this->getDataGenerator()->create_user();
|
||||
$user4 = $this->getDataGenerator()->create_user();
|
||||
|
||||
// This user will not be added as a contact.
|
||||
$this->getDataGenerator()->create_user();
|
||||
|
||||
message_add_contact($user2->id, 0, $user1->id);
|
||||
message_add_contact($user3->id, 0, $user1->id);
|
||||
message_add_contact($user4->id, 1, $user1->id);
|
||||
|
||||
$this->export_context_data_for_user($user1->id, \context_system::instance(), 'core_message');
|
||||
|
||||
$writer = writer::with_context(\context_system::instance());
|
||||
|
||||
$contacts = (array) $writer->get_data([get_string('contacts', 'core_message')]);
|
||||
|
||||
$this->assertCount(3, $contacts);
|
||||
|
||||
$contact1 = array_shift($contacts);
|
||||
$this->assertEquals($user2->id, $contact1->contact);
|
||||
$this->assertEquals(get_string('no'), $contact1->blocked);
|
||||
|
||||
$contact2 = array_shift($contacts);
|
||||
$this->assertEquals($user3->id, $contact2->contact);
|
||||
$this->assertEquals(get_string('no'), $contact2->blocked);
|
||||
|
||||
$contact3 = array_shift($contacts);
|
||||
$this->assertEquals($user4->id, $contact3->contact);
|
||||
$this->assertEquals(get_string('yes'), $contact3->blocked);
|
||||
}
|
||||
|
||||
/**
|
||||
* Test for provider::export_user_data().
|
||||
*/
|
||||
public function test_export_for_context_with_messages() {
|
||||
global $DB;
|
||||
|
||||
$this->resetAfterTest();
|
||||
|
||||
// Create users to test with.
|
||||
$user1 = $this->getDataGenerator()->create_user();
|
||||
$user2 = $this->getDataGenerator()->create_user();
|
||||
$user3 = $this->getDataGenerator()->create_user();
|
||||
|
||||
$now = time();
|
||||
|
||||
// Send messages from user 1 to user 2.
|
||||
$m1 = $this->create_message($user1->id, $user2->id, $now - (9 * DAYSECS), true);
|
||||
$m2 = $this->create_message($user2->id, $user1->id, $now - (8 * DAYSECS));
|
||||
$m3 = $this->create_message($user1->id, $user2->id, $now - (7 * DAYSECS));
|
||||
|
||||
// Send messages from user 3 to user 1.
|
||||
$m4 = $this->create_message($user3->id, $user1->id, $now - (6 * DAYSECS), true);
|
||||
$m5 = $this->create_message($user1->id, $user3->id, $now - (5 * DAYSECS));
|
||||
$m6 = $this->create_message($user3->id, $user1->id, $now - (4 * DAYSECS));
|
||||
|
||||
// Send messages from user 3 to user 2 - these should not be included in the export.
|
||||
$m7 = $this->create_message($user3->id, $user2->id, $now - (3 * DAYSECS), true);
|
||||
$m8 = $this->create_message($user2->id, $user3->id, $now - (2 * DAYSECS));
|
||||
$m9 = $this->create_message($user3->id, $user2->id, $now - (1 * DAYSECS));
|
||||
|
||||
// Mark message 2 and 5 as deleted.
|
||||
\core_message\api::delete_message($user1->id, $m2);
|
||||
\core_message\api::delete_message($user1->id, $m5);
|
||||
|
||||
$this->export_context_data_for_user($user1->id, \context_system::instance(), 'core_message');
|
||||
|
||||
$writer = writer::with_context(\context_system::instance());
|
||||
|
||||
$this->assertTrue($writer->has_any_data());
|
||||
|
||||
// Confirm the messages with user 2 are correct.
|
||||
$messages = (array) $writer->get_data([get_string('messages', 'core_message'), fullname($user2)]);
|
||||
$this->assertCount(3, $messages);
|
||||
|
||||
$dbm1 = $DB->get_record('messages', ['id' => $m1]);
|
||||
$dbm2 = $DB->get_record('messages', ['id' => $m2]);
|
||||
$dbm3 = $DB->get_record('messages', ['id' => $m3]);
|
||||
|
||||
$m1 = array_shift($messages);
|
||||
$m2 = array_shift($messages);
|
||||
$m3 = array_shift($messages);
|
||||
|
||||
$this->assertEquals(get_string('yes'), $m1->sender);
|
||||
$this->assertEquals(message_format_message_text($dbm1), $m1->message);
|
||||
$this->assertEquals(transform::datetime($now - (9 * DAYSECS)), $m1->timecreated);
|
||||
$this->assertNotEquals('-', $m1->timeread);
|
||||
$this->assertArrayNotHasKey('timedeleted', (array) $m1);
|
||||
|
||||
$this->assertEquals(get_string('no'), $m2->sender);
|
||||
$this->assertEquals(message_format_message_text($dbm2), $m2->message);
|
||||
$this->assertEquals(transform::datetime($now - (8 * DAYSECS)), $m2->timecreated);
|
||||
$this->assertEquals('-', $m2->timeread);
|
||||
$this->assertArrayHasKey('timedeleted', (array) $m2);
|
||||
|
||||
$this->assertEquals(get_string('yes'), $m3->sender);
|
||||
$this->assertEquals(message_format_message_text($dbm3), $m3->message);
|
||||
$this->assertEquals(transform::datetime($now - (7 * DAYSECS)), $m3->timecreated);
|
||||
$this->assertEquals('-', $m3->timeread);
|
||||
|
||||
// Confirm the messages with user 3 are correct.
|
||||
$messages = (array) $writer->get_data([get_string('messages', 'core_message'), fullname($user3)]);
|
||||
$this->assertCount(3, $messages);
|
||||
|
||||
$dbm4 = $DB->get_record('messages', ['id' => $m4]);
|
||||
$dbm5 = $DB->get_record('messages', ['id' => $m5]);
|
||||
$dbm6 = $DB->get_record('messages', ['id' => $m6]);
|
||||
|
||||
$m4 = array_shift($messages);
|
||||
$m5 = array_shift($messages);
|
||||
$m6 = array_shift($messages);
|
||||
|
||||
$this->assertEquals(get_string('no'), $m4->sender);
|
||||
$this->assertEquals(message_format_message_text($dbm4), $m4->message);
|
||||
$this->assertEquals(transform::datetime($now - (6 * DAYSECS)), $m4->timecreated);
|
||||
$this->assertNotEquals('-', $m4->timeread);
|
||||
$this->assertArrayNotHasKey('timedeleted', (array) $m4);
|
||||
|
||||
$this->assertEquals(get_string('yes'), $m5->sender);
|
||||
$this->assertEquals(message_format_message_text($dbm5), $m5->message);
|
||||
$this->assertEquals(transform::datetime($now - (5 * DAYSECS)), $m5->timecreated);
|
||||
$this->assertEquals('-', $m5->timeread);
|
||||
$this->assertArrayHasKey('timedeleted', (array) $m5);
|
||||
|
||||
$this->assertEquals(get_string('no'), $m6->sender);
|
||||
$this->assertEquals(message_format_message_text($dbm6), $m6->message);
|
||||
$this->assertEquals(transform::datetime($now - (4 * DAYSECS)), $m6->timecreated);
|
||||
$this->assertEquals('-', $m6->timeread);
|
||||
}
|
||||
|
||||
/**
|
||||
* Test for provider::export_user_data().
|
||||
*/
|
||||
public function test_export_for_context_with_notifications() {
|
||||
$this->resetAfterTest();
|
||||
|
||||
// Create users to test with.
|
||||
$user1 = $this->getDataGenerator()->create_user();
|
||||
$user2 = $this->getDataGenerator()->create_user();
|
||||
$user3 = $this->getDataGenerator()->create_user();
|
||||
|
||||
$now = time();
|
||||
$timeread = $now - DAYSECS;
|
||||
|
||||
// Send notifications from user 1 to user 2.
|
||||
$this->create_notification($user1->id, $user2->id, $now + (9 * DAYSECS), $timeread);
|
||||
$this->create_notification($user2->id, $user1->id, $now + (8 * DAYSECS));
|
||||
$this->create_notification($user1->id, $user2->id, $now + (7 * DAYSECS));
|
||||
|
||||
// Send notifications from user 3 to user 1.
|
||||
$this->create_notification($user3->id, $user1->id, $now + (6 * DAYSECS), $timeread);
|
||||
$this->create_notification($user1->id, $user3->id, $now + (5 * DAYSECS));
|
||||
$this->create_notification($user3->id, $user1->id, $now + (4 * DAYSECS));
|
||||
|
||||
// Send notifications from user 3 to user 2 - should not be part of the export.
|
||||
$this->create_notification($user3->id, $user2->id, $now + (3 * DAYSECS), $timeread);
|
||||
$this->create_notification($user2->id, $user3->id, $now + (2 * DAYSECS));
|
||||
$this->create_notification($user3->id, $user2->id, $now + (1 * DAYSECS));
|
||||
|
||||
$this->export_context_data_for_user($user1->id, \context_system::instance(), 'core_message');
|
||||
|
||||
$writer = writer::with_context(\context_system::instance());
|
||||
|
||||
$this->assertTrue($writer->has_any_data());
|
||||
|
||||
// Confirm the notifications.
|
||||
$notifications = (array) $writer->get_data([get_string('notifications', 'core_message')]);
|
||||
|
||||
$this->assertCount(6, $notifications);
|
||||
}
|
||||
|
||||
/**
|
||||
* Test for provider::delete_data_for_all_users_in_context().
|
||||
*/
|
||||
public function test_delete_data_for_all_users_in_context() {
|
||||
global $DB;
|
||||
|
||||
$this->resetAfterTest();
|
||||
|
||||
// Create users to test with.
|
||||
$user1 = $this->getDataGenerator()->create_user();
|
||||
$user2 = $this->getDataGenerator()->create_user();
|
||||
|
||||
$now = time();
|
||||
$timeread = $now - DAYSECS;
|
||||
|
||||
$systemcontext = \context_system::instance();
|
||||
|
||||
// Create contacts.
|
||||
message_add_contact($user1->id, 0, $user2->id);
|
||||
message_add_contact($user2->id, 0, $user1->id);
|
||||
|
||||
// Create messages.
|
||||
$m1 = $this->create_message($user1->id, $user2->id, $now + (9 * DAYSECS), true);
|
||||
$m2 = $this->create_message($user2->id, $user1->id, $now + (8 * DAYSECS));
|
||||
|
||||
// Create notifications.
|
||||
$n1 = $this->create_notification($user1->id, $user2->id, $now + (9 * DAYSECS), $timeread);
|
||||
$n2 = $this->create_notification($user2->id, $user1->id, $now + (8 * DAYSECS));
|
||||
|
||||
// Delete one of the messages.
|
||||
\core_message\api::delete_message($user1->id, $m2);
|
||||
|
||||
// There should be 2 contacts.
|
||||
$this->assertEquals(2, $DB->count_records('message_contacts'));
|
||||
|
||||
// There should be two messages.
|
||||
$this->assertEquals(2, $DB->count_records('messages'));
|
||||
|
||||
// There should be two user actions - one for reading the message, one for deleting.
|
||||
$this->assertEquals(2, $DB->count_records('message_user_actions'));
|
||||
|
||||
// There should be two conversation members.
|
||||
$this->assertEquals(2, $DB->count_records('message_conversation_members'));
|
||||
|
||||
// There should be two notifications.
|
||||
$this->assertEquals(2, $DB->count_records('notifications'));
|
||||
|
||||
provider::delete_data_for_all_users_in_context($systemcontext);
|
||||
|
||||
// Confirm all has been deleted.
|
||||
$this->assertEquals(0, $DB->count_records('message_contacts'));
|
||||
$this->assertEquals(0, $DB->count_records('messages'));
|
||||
$this->assertEquals(0, $DB->count_records('message_user_actions'));
|
||||
$this->assertEquals(0, $DB->count_records('message_conversation_members'));
|
||||
$this->assertEquals(0, $DB->count_records('notifications'));
|
||||
}
|
||||
|
||||
/**
|
||||
* Test for provider::delete_data_for_user().
|
||||
*/
|
||||
public function test_delete_data_for_user() {
|
||||
global $DB;
|
||||
|
||||
$this->resetAfterTest();
|
||||
|
||||
// Create users to test with.
|
||||
$user1 = $this->getDataGenerator()->create_user();
|
||||
$user2 = $this->getDataGenerator()->create_user();
|
||||
$user3 = $this->getDataGenerator()->create_user();
|
||||
|
||||
$now = time();
|
||||
$timeread = $now - DAYSECS;
|
||||
|
||||
// Create contacts.
|
||||
message_add_contact($user1->id, 0, $user2->id);
|
||||
message_add_contact($user2->id, 0, $user1->id);
|
||||
message_add_contact($user2->id, 0, $user3->id);
|
||||
|
||||
// Create messages.
|
||||
$m1 = $this->create_message($user1->id, $user2->id, $now + (9 * DAYSECS), $timeread);
|
||||
$m2 = $this->create_message($user2->id, $user1->id, $now + (8 * DAYSECS));
|
||||
|
||||
// Create notifications.
|
||||
$n1 = $this->create_notification($user1->id, $user2->id, $now + (9 * DAYSECS), $timeread);
|
||||
$n2 = $this->create_notification($user2->id, $user1->id, $now + (8 * DAYSECS));
|
||||
$n2 = $this->create_notification($user2->id, $user3->id, $now + (8 * DAYSECS));
|
||||
|
||||
// Delete one of the messages.
|
||||
\core_message\api::delete_message($user1->id, $m2);
|
||||
|
||||
// There should be 3 contacts.
|
||||
$this->assertEquals(3, $DB->count_records('message_contacts'));
|
||||
|
||||
// There should be two messages.
|
||||
$this->assertEquals(2, $DB->count_records('messages'));
|
||||
|
||||
// There should be two user actions - one for reading the message, one for deleting.
|
||||
$this->assertEquals(2, $DB->count_records('message_user_actions'));
|
||||
|
||||
// There should be two conversation members.
|
||||
$this->assertEquals(2, $DB->count_records('message_conversation_members'));
|
||||
|
||||
// There should be three notifications.
|
||||
$this->assertEquals(3, $DB->count_records('notifications'));
|
||||
|
||||
$systemcontext = \context_system::instance();
|
||||
$contextlist = new \core_privacy\local\request\approved_contextlist($user1, 'core_message',
|
||||
[$systemcontext->id]);
|
||||
provider::delete_data_for_user($contextlist);
|
||||
|
||||
// Confirm the user 2 data still exists.
|
||||
$contacts = $DB->get_records('message_contacts');
|
||||
$messages = $DB->get_records('messages');
|
||||
$muas = $DB->get_records('message_user_actions');
|
||||
$mcms = $DB->get_records('message_conversation_members');
|
||||
$notifications = $DB->get_records('notifications');
|
||||
|
||||
$this->assertCount(1, $contacts);
|
||||
$contact = reset($contacts);
|
||||
$this->assertEquals($user3->id, $contact->userid);
|
||||
$this->assertEquals($user2->id, $contact->contactid);
|
||||
|
||||
$this->assertCount(1, $messages);
|
||||
$message = reset($messages);
|
||||
$this->assertEquals($m2, $message->id);
|
||||
|
||||
$this->assertCount(1, $muas);
|
||||
$mua = reset($muas);
|
||||
$this->assertEquals($user2->id, $mua->userid);
|
||||
$this->assertEquals($m1, $mua->messageid);
|
||||
$this->assertEquals(\core_message\api::MESSAGE_ACTION_READ, $mua->action);
|
||||
|
||||
$this->assertCount(1, $mcms);
|
||||
$mcm = reset($mcms);
|
||||
$this->assertEquals($user2->id, $mcm->userid);
|
||||
|
||||
$this->assertCount(1, $notifications);
|
||||
$notification = reset($notifications);
|
||||
$this->assertEquals($user2->id, $notification->useridfrom);
|
||||
$this->assertEquals($user3->id, $notification->useridto);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a message to be used for testing.
|
||||
*
|
||||
* @param int $useridfrom The user id from
|
||||
* @param int $useridto The user id to
|
||||
* @param int $timecreated
|
||||
* @param bool $read Do we want to mark the message as read?
|
||||
* @return int The id of the message
|
||||
* @throws dml_exception
|
||||
*/
|
||||
private function create_message(int $useridfrom, int $useridto, int $timecreated = null, bool $read = false) {
|
||||
global $DB;
|
||||
|
||||
static $i = 1;
|
||||
|
||||
if (is_null($timecreated)) {
|
||||
$timecreated = time();
|
||||
}
|
||||
|
||||
if (!$conversationid = \core_message\api::get_conversation_between_users([$useridfrom, $useridto])) {
|
||||
$conversationid = \core_message\api::create_conversation_between_users([$useridfrom,
|
||||
$useridto]);
|
||||
}
|
||||
|
||||
// Ok, send the message.
|
||||
$record = new stdClass();
|
||||
$record->useridfrom = $useridfrom;
|
||||
$record->conversationid = $conversationid;
|
||||
$record->subject = 'No subject';
|
||||
$record->fullmessage = 'A rad message ' . $i;
|
||||
$record->smallmessage = 'A rad message ' . $i;
|
||||
$record->timecreated = $timecreated;
|
||||
|
||||
$i++;
|
||||
|
||||
$record->id = $DB->insert_record('messages', $record);
|
||||
|
||||
if ($read) {
|
||||
\core_message\api::mark_message_as_read($useridto, $record);
|
||||
}
|
||||
|
||||
return $record->id;
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a notification to be used for testing.
|
||||
*
|
||||
* @param int $useridfrom The user id from
|
||||
* @param int $useridto The user id to
|
||||
* @param int|null $timecreated The time the notification was created
|
||||
* @param int|null $timeread The time the notification was read, null if it hasn't been.
|
||||
* @return int The id of the notification
|
||||
* @throws dml_exception
|
||||
*/
|
||||
private function create_notification(int $useridfrom, int $useridto, int $timecreated = null, int $timeread = null) {
|
||||
global $DB;
|
||||
|
||||
static $i = 1;
|
||||
|
||||
if (is_null($timecreated)) {
|
||||
$timecreated = time();
|
||||
}
|
||||
|
||||
$record = new stdClass();
|
||||
$record->useridfrom = $useridfrom;
|
||||
$record->useridto = $useridto;
|
||||
$record->subject = 'No subject';
|
||||
$record->fullmessage = 'Some rad notification ' . $i;
|
||||
$record->smallmessage = 'Yo homie, you got some stuff to do, yolo. ' . $i;
|
||||
$record->timeread = $timeread;
|
||||
$record->timecreated = $timecreated;
|
||||
|
||||
$i++;
|
||||
|
||||
return $DB->insert_record('notifications', $record);
|
||||
}
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user