From 9b8822d2a662699ab9121b8684e4242309f6e91b Mon Sep 17 00:00:00 2001 From: Mihail Geshoski Date: Tue, 10 Apr 2018 09:34:38 +0800 Subject: [PATCH] MDL-61795 block_rss_client: Add privacy files and unit tests --- blocks/rss_client/classes/privacy/provider.php | 145 +++++++++++++++++++++++++ blocks/rss_client/lang/en/block_rss_client.php | 9 ++ blocks/rss_client/tests/privacy_test.php | 145 +++++++++++++++++++++++++ 3 files changed, 299 insertions(+) create mode 100644 blocks/rss_client/classes/privacy/provider.php create mode 100644 blocks/rss_client/tests/privacy_test.php diff --git a/blocks/rss_client/classes/privacy/provider.php b/blocks/rss_client/classes/privacy/provider.php new file mode 100644 index 00000000000..d37f27fb72f --- /dev/null +++ b/blocks/rss_client/classes/privacy/provider.php @@ -0,0 +1,145 @@ +. +/** + * Privacy class for requesting user data. + * + * @package block_rss_client + * @copyright 2018 Mihail Geshoski + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ + +namespace block_rss_client\privacy; + +defined('MOODLE_INTERNAL') || die(); + +use \core_privacy\local\metadata\collection; +use \core_privacy\local\request\contextlist; +use \core_privacy\local\request\approved_contextlist; + +/** + * Privacy class for requesting user data. + * + * @package block_rss_client + * @copyright 2018 Mihail Geshoski + * @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\plugin\provider { + + /** + * Returns meta data about this system. + * + * @param collection $collection The initialised collection to add items to. + * @return collection A listing of user data stored through this system. + */ + public static function get_metadata(collection $collection) : collection { + $collection->add_database_table('block_rss_client', [ + 'userid' => 'privacy:metadata:block_rss_client:userid', + 'title' => 'privacy:metadata:block_rss_client:title', + 'preferredtitle' => 'privacy:metadata:block_rss_client:preferredtitle', + 'description' => 'privacy:metadata:block_rss_client:description', + 'shared' => 'privacy:metadata:block_rss_client:shared', + 'url' => 'privacy:metadata:block_rss_client:url', + 'skiptime' => 'privacy:metadata:block_rss_client:skiptime', + 'skipuntil' => 'privacy:metadata:block_rss_client:skipuntil', + ], 'privacy:metadata:block_rss_client:tableexplanation'); + return $collection; + } + + /** + * Get the list of contexts that contain user information for the specified user. + * + * @param int $userid The user to search. + * @return contextlist $contextlist The contextlist containing the list of contexts used in this plugin. + */ + public static function get_contexts_for_userid(int $userid) : contextlist { + $sql = "SELECT ctx.id + FROM {block_rss_client} brc + JOIN {user} u + ON brc.userid = u.id + JOIN {context} ctx + ON ctx.instanceid = u.id + AND ctx.contextlevel = :contextlevel + WHERE brc.userid = :userid"; + + $params = ['userid' => $userid, 'contextlevel' => CONTEXT_USER]; + + $contextlist = new contextlist(); + $contextlist->add_from_sql($sql, $params); + return $contextlist; + } + + /** + * Export all user data for the specified user, in the specified contexts. + * + * @param approved_contextlist $contextlist The approved contexts to export information for. + */ + public static function export_user_data(approved_contextlist $contextlist) { + $results = static::get_records($contextlist->get_user()->id); + foreach ($results as $result) { + $data = (object) [ + 'title' => $result->title, + 'preferredtitle' => $result->preferredtitle, + 'description' => $result->description, + 'shared' => \core_privacy\local\request\transform::yesno($result->shared), + 'url' => $result->url + ]; + + \core_privacy\local\request\writer::with_context($contextlist->current())->export_data([ + get_string('pluginname', 'block_rss_client')], $data); + } + } + + /** + * Delete all use data which matches the specified deletion_criteria. + * + * @param context $context A user context. + */ + public static function delete_data_for_all_users_in_context(\context $context) { + static::delete_data($context->instanceid); + } + + /** + * Delete all user data for the specified user, in the specified contexts. + * + * @param approved_contextlist $contextlist The approved contexts and user information to delete information for. + */ + public static function delete_data_for_user(approved_contextlist $contextlist) { + static::delete_data($contextlist->get_user()->id); + } + + /** + * Delete data related to a userid. + * + * @param int $userid The user ID + */ + protected static function delete_data($userid) { + global $DB; + + $DB->delete_records('block_rss_client', ['userid' => $userid]); + } + + /** + * Get records related to this plugin and user. + * + * @param int $userid The user ID + * @return array An array of records. + */ + protected static function get_records($userid) { + global $DB; + + return $DB->get_records('block_rss_client', ['userid' => $userid]); + } +} diff --git a/blocks/rss_client/lang/en/block_rss_client.php b/blocks/rss_client/lang/en/block_rss_client.php index e606979018a..3045074fc53 100644 --- a/blocks/rss_client/lang/en/block_rss_client.php +++ b/blocks/rss_client/lang/en/block_rss_client.php @@ -62,6 +62,15 @@ $string['nofeeds'] = 'There are no RSS feeds defined for this site.'; $string['numentries'] = 'Entries per feed'; $string['pickfeed'] = 'Pick a news feed'; $string['pluginname'] = 'Remote RSS feeds'; +$string['privacy:metadata:block_rss_client:description'] = 'The description of the RSS feed.'; +$string['privacy:metadata:block_rss_client:preferredtitle'] = 'The preferred (custom) title of the RSS feed.'; +$string['privacy:metadata:block_rss_client:shared'] = 'If the RSS feed is available to all courses.'; +$string['privacy:metadata:block_rss_client:skiptime'] = 'The defined time in seconds that the cron will wait between attempts to retry failing RSS feeds.'; +$string['privacy:metadata:block_rss_client:skipuntil'] = 'The maximum defined time that the cron will attempt to open failing RSS feeds.'; +$string['privacy:metadata:block_rss_client:tableexplanation'] = 'RSS block information is stored here.'; +$string['privacy:metadata:block_rss_client:title'] = 'The title of the RSS feed.'; +$string['privacy:metadata:block_rss_client:url'] = 'The URL of the RSS feed.'; +$string['privacy:metadata:block_rss_client:userid'] = 'The ID of the user that added the RSS feed.'; $string['remotenewsfeed'] = 'Remote news feed'; $string['rss_client:addinstance'] = 'Add a new remote RSS feeds block'; $string['rss_client:createprivatefeeds'] = 'Create private RSS feeds'; diff --git a/blocks/rss_client/tests/privacy_test.php b/blocks/rss_client/tests/privacy_test.php new file mode 100644 index 00000000000..dfd37c13eed --- /dev/null +++ b/blocks/rss_client/tests/privacy_test.php @@ -0,0 +1,145 @@ +. +/** + * Base class for unit tests for block_rss_client. + * + * @package block_rss_client + * @copyright 2018 Mihail Geshoski + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ + +defined('MOODLE_INTERNAL') || die(); + +use \core_privacy\tests\provider_testcase; + +/** + * Unit tests for blocks\rss_client\classes\privacy\provider.php + * + * @copyright 2018 Mihail Geshoski + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ +class block_rss_client_testcase extends provider_testcase { + + /** + * Basic setup for these tests. + */ + public function setUp() { + $this->resetAfterTest(true); + } + + /** + * Test getting the context for the user ID related to this plugin. + */ + public function test_get_contexts_for_userid() { + + $user = $this->getDataGenerator()->create_user(); + $context = context_user::instance($user->id); + + $this->add_rss_feed($user); + + $contextlist = \block_rss_client\privacy\provider::get_contexts_for_userid($user->id); + + $this->assertEquals($context, $contextlist->current()); + } + + /** + * Test that data is exported correctly for this plugin. + */ + public function test_export_user_data() { + + $user = $this->getDataGenerator()->create_user(); + $context = context_user::instance($user->id); + + $this->add_rss_feed($user); + + $writer = \core_privacy\local\request\writer::with_context($context); + $this->assertFalse($writer->has_any_data()); + $this->export_context_data_for_user($user->id, $context, 'block_rss_client'); + + $data = $writer->get_data([get_string('pluginname', 'block_rss_client')]); + $this->assertEquals('BBC News - World', $data->title); + $this->assertEquals('World News', $data->preferredtitle); + $this->assertEquals('Description: BBC News - World', $data->description); + $this->assertEquals(get_string('no'), $data->shared); + $this->assertEquals('http://feeds.bbci.co.uk/news/world/rss.xml?edition=uk', $data->url); + } + + /** + * Test that user data is deleted using the context. + */ + public function test_delete_data_for_all_users_in_context() { + global $DB; + + $user = $this->getDataGenerator()->create_user(); + $context = context_user::instance($user->id); + + $this->add_rss_feed($user); + + // Check that we have an entry. + $rssfeeds = $DB->get_records('block_rss_client', ['userid' => $user->id]); + $this->assertCount(1, $rssfeeds); + + \block_rss_client\privacy\provider::delete_data_for_all_users_in_context($context); + + // Check that it has now been deleted. + $rssfeeds = $DB->get_records('block_rss_client', ['userid' => $user->id]); + $this->assertCount(0, $rssfeeds); + } + + /** + * Test that user data is deleted for this user. + */ + public function test_delete_data_for_user() { + global $DB; + + $user = $this->getDataGenerator()->create_user(); + $context = context_user::instance($user->id); + + $this->add_rss_feed($user); + + // Check that we have an entry. + $rssfeeds = $DB->get_records('block_rss_client', ['userid' => $user->id]); + $this->assertCount(1, $rssfeeds); + + $approvedlist = new \core_privacy\local\request\approved_contextlist($user, 'block_rss_feed', + [$context->id]); + \block_rss_client\privacy\provider::delete_data_for_user($approvedlist); + + // Check that it has now been deleted. + $rssfeeds = $DB->get_records('block_rss_client', ['userid' => $user->id]); + $this->assertCount(0, $rssfeeds); + } + + /** + * Add dummy rss feed. + * + * @param object $user User object + */ + private function add_rss_feed($user) { + global $DB; + + $rssfeeddata = array( + 'userid' => $user->id, + 'title' => 'BBC News - World', + 'preferredtitle' => 'World News', + 'description' => 'Description: BBC News - World', + 'shared' => 0, + 'url' => 'http://feeds.bbci.co.uk/news/world/rss.xml?edition=uk', + ); + + $DB->insert_record('block_rss_client', $rssfeeddata); + } +} -- 2.11.4.GIT