Merge branch 'MDL-68443-xmldb-path-validation-MOODLE_37_STABLE' of https://github...
[moodle.git] / blocks / tests / privacy_test.php
blob20df9d9fecb4de1f4ec7a078e11288727dc0f9a2
1 <?php
2 // This file is part of Moodle - http://moodle.org/
3 //
4 // Moodle is free software: you can redistribute it and/or modify
5 // it under the terms of the GNU General Public License as published by
6 // the Free Software Foundation, either version 3 of the License, or
7 // (at your option) any later version.
8 //
9 // Moodle is distributed in the hope that it will be useful,
10 // but WITHOUT ANY WARRANTY; without even the implied warranty of
11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 // GNU General Public License for more details.
14 // You should have received a copy of the GNU General Public License
15 // along with Moodle. If not, see <http://www.gnu.org/licenses/>.
17 /**
18 * Data provider tests.
20 * @package core_block
21 * @category test
22 * @copyright 2018 Frédéric Massart
23 * @author Frédéric Massart <fred@branchup.tech>
24 * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
27 defined('MOODLE_INTERNAL') || die();
28 global $CFG;
30 use core_privacy\tests\provider_testcase;
31 use core_privacy\local\request\approved_contextlist;
32 use core_privacy\local\request\transform;
33 use core_privacy\local\request\writer;
34 use core_block\privacy\provider;
36 /**
37 * Data provider testcase class.
39 * @package core_block
40 * @category test
41 * @copyright 2018 Frédéric Massart
42 * @author Frédéric Massart <fred@branchup.tech>
43 * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
45 class core_block_privacy_testcase extends provider_testcase {
47 public function setUp() {
48 $this->resetAfterTest();
51 public function test_get_contexts_for_userid() {
52 $dg = $this->getDataGenerator();
53 $c1 = $dg->create_course();
54 $c2 = $dg->create_course();
55 $u1 = $dg->create_user();
56 $u2 = $dg->create_user();
57 $c1ctx = context_course::instance($c1->id);
58 $c2ctx = context_course::instance($c2->id);
59 $u1ctx = context_user::instance($u1->id);
60 $u2ctx = context_user::instance($u2->id);
62 $manager = $this->get_block_manager(['region-a'], $c1ctx);
63 $manager->add_block('myprofile', 'region-a', 0, false);
64 $manager->load_blocks();
65 $blockmyprofile = $manager->get_blocks_for_region('region-a')[0];
67 $manager = $this->get_block_manager(['region-a'], $c2ctx);
68 $manager->add_block('login', 'region-a', 0, false);
69 $manager->add_block('mentees', 'region-a', 1, false);
70 $manager->load_blocks();
71 list($blocklogin, $blockmentees) = $manager->get_blocks_for_region('region-a');
73 $manager = $this->get_block_manager(['region-a'], $u1ctx);
74 $manager->add_block('private_files', 'region-a', 0, false);
75 $manager->load_blocks();
76 $blockprivatefiles = $manager->get_blocks_for_region('region-a')[0];
78 $this->set_hidden_pref($blocklogin, true, $u1->id);
79 $this->set_hidden_pref($blockprivatefiles, true, $u1->id);
80 $this->set_docked_pref($blockmyprofile, true, $u1->id);
81 $this->set_docked_pref($blockmentees, true, $u1->id);
82 $this->set_docked_pref($blockmentees, true, $u2->id);
84 $contextids = provider::get_contexts_for_userid($u1->id)->get_contextids();
85 $this->assertCount(4, $contextids);
86 $this->assertTrue(in_array($blocklogin->context->id, $contextids));
87 $this->assertTrue(in_array($blockprivatefiles->context->id, $contextids));
88 $this->assertTrue(in_array($blockmyprofile->context->id, $contextids));
89 $this->assertTrue(in_array($blockmentees->context->id, $contextids));
91 $contextids = provider::get_contexts_for_userid($u2->id)->get_contextids();
92 $this->assertCount(1, $contextids);
93 $this->assertTrue(in_array($blockmentees->context->id, $contextids));
96 /**
97 * Test that user IDs are returned for a given context.
99 public function test_get_users_in_context() {
100 global $DB;
101 $u1 = $this->getDataGenerator()->create_user();
102 $u2 = $this->getDataGenerator()->create_user();
103 $u3 = $this->getDataGenerator()->create_user();
105 $course = $this->getDataGenerator()->create_course();
107 $manager = $this->get_block_manager(['region-a'], context_course::instance($course->id));
108 $manager->add_block('myprofile', 'region-a', 0, false);
109 $manager->load_blocks();
110 $blockmyprofile = $manager->get_blocks_for_region('region-a')[0];
112 $this->set_hidden_pref($blockmyprofile, true, $u1->id);
113 $this->set_hidden_pref($blockmyprofile, true, $u3->id);
114 $this->set_docked_pref($blockmyprofile, true, $u2->id);
115 $this->set_docked_pref($blockmyprofile, true, $u3->id);
117 $records = $DB->get_records('block_instances', ['blockname' => 'myprofile']);
118 $record = array_shift($records);
119 $blockcontext = context_block::instance($record->id);
121 $userlist = new \core_privacy\local\request\userlist($blockcontext, 'core_block');
122 provider::get_users_in_context($userlist);
123 $this->assertCount(3, $userlist->get_userids());
127 public function test_delete_data_for_user() {
128 global $DB;
129 $dg = $this->getDataGenerator();
130 $c1 = $dg->create_course();
131 $c2 = $dg->create_course();
132 $u1 = $dg->create_user();
133 $u2 = $dg->create_user();
134 $c1ctx = context_course::instance($c1->id);
135 $c2ctx = context_course::instance($c2->id);
136 $u1ctx = context_user::instance($u1->id);
137 $u2ctx = context_user::instance($u2->id);
139 $manager = $this->get_block_manager(['region-a'], $c1ctx);
140 $manager->add_block('myprofile', 'region-a', 0, false);
141 $manager->load_blocks();
142 $blockmyprofile = $manager->get_blocks_for_region('region-a')[0];
144 $manager = $this->get_block_manager(['region-a'], $c2ctx);
145 $manager->add_block('login', 'region-a', 0, false);
146 $manager->add_block('mentees', 'region-a', 1, false);
147 $manager->load_blocks();
148 list($blocklogin, $blockmentees) = $manager->get_blocks_for_region('region-a');
150 $manager = $this->get_block_manager(['region-a'], $u1ctx);
151 $manager->add_block('private_files', 'region-a', 0, false);
152 $manager->load_blocks();
153 $blockprivatefiles = $manager->get_blocks_for_region('region-a')[0];
155 $this->set_hidden_pref($blocklogin, true, $u1->id);
156 $this->set_hidden_pref($blocklogin, true, $u2->id);
157 $this->set_hidden_pref($blockprivatefiles, true, $u1->id);
158 $this->set_hidden_pref($blockmyprofile, true, $u1->id);
159 $this->set_docked_pref($blockmyprofile, true, $u1->id);
160 $this->set_docked_pref($blockmentees, true, $u1->id);
161 $this->set_docked_pref($blockmentees, true, $u2->id);
163 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
164 'name' => "block{$blocklogin->instance->id}hidden"]));
165 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u2->id,
166 'name' => "block{$blocklogin->instance->id}hidden"]));
167 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
168 'name' => "block{$blockprivatefiles->instance->id}hidden"]));
169 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
170 'name' => "block{$blockmyprofile->instance->id}hidden"]));
171 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
172 'name' => "docked_block_instance_{$blockmyprofile->instance->id}"]));
173 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
174 'name' => "docked_block_instance_{$blockmentees->instance->id}"]));
175 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u2->id,
176 'name' => "docked_block_instance_{$blockmentees->instance->id}"]));
178 provider::delete_data_for_user(new approved_contextlist($u1, 'core_block', [$blocklogin->context->id,
179 $blockmyprofile->context->id, $blockmentees->context->id]));
181 $this->assertFalse($DB->record_exists('user_preferences', ['userid' => $u1->id,
182 'name' => "block{$blocklogin->instance->id}hidden"]));
183 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u2->id,
184 'name' => "block{$blocklogin->instance->id}hidden"]));
185 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
186 'name' => "block{$blockprivatefiles->instance->id}hidden"]));
187 $this->assertFalse($DB->record_exists('user_preferences', ['userid' => $u1->id,
188 'name' => "block{$blockmyprofile->instance->id}hidden"]));
189 $this->assertFalse($DB->record_exists('user_preferences', ['userid' => $u1->id,
190 'name' => "docked_block_instance_{$blockmyprofile->instance->id}"]));
191 $this->assertFalse($DB->record_exists('user_preferences', ['userid' => $u1->id,
192 'name' => "docked_block_instance_{$blockmentees->instance->id}"]));
193 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u2->id,
194 'name' => "docked_block_instance_{$blockmentees->instance->id}"]));
197 public function test_delete_data_for_all_users_in_context() {
198 global $DB;
199 $dg = $this->getDataGenerator();
200 $c1 = $dg->create_course();
201 $c2 = $dg->create_course();
202 $u1 = $dg->create_user();
203 $u2 = $dg->create_user();
204 $c1ctx = context_course::instance($c1->id);
205 $c2ctx = context_course::instance($c2->id);
206 $u1ctx = context_user::instance($u1->id);
207 $u2ctx = context_user::instance($u2->id);
209 $manager = $this->get_block_manager(['region-a'], $c1ctx);
210 $manager->add_block('myprofile', 'region-a', 0, false);
211 $manager->load_blocks();
212 $blockmyprofile = $manager->get_blocks_for_region('region-a')[0];
214 $manager = $this->get_block_manager(['region-a'], $c2ctx);
215 $manager->add_block('login', 'region-a', 0, false);
216 $manager->add_block('mentees', 'region-a', 1, false);
217 $manager->load_blocks();
218 list($blocklogin, $blockmentees) = $manager->get_blocks_for_region('region-a');
220 $manager = $this->get_block_manager(['region-a'], $u1ctx);
221 $manager->add_block('private_files', 'region-a', 0, false);
222 $manager->load_blocks();
223 $blockprivatefiles = $manager->get_blocks_for_region('region-a')[0];
225 $this->set_hidden_pref($blocklogin, true, $u1->id);
226 $this->set_hidden_pref($blocklogin, true, $u2->id);
227 $this->set_hidden_pref($blockprivatefiles, true, $u1->id);
228 $this->set_hidden_pref($blockmyprofile, true, $u1->id);
229 $this->set_docked_pref($blockmyprofile, true, $u1->id);
230 $this->set_docked_pref($blockmentees, true, $u1->id);
231 $this->set_docked_pref($blockmentees, true, $u2->id);
233 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
234 'name' => "block{$blocklogin->instance->id}hidden"]));
235 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u2->id,
236 'name' => "block{$blocklogin->instance->id}hidden"]));
237 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
238 'name' => "block{$blockprivatefiles->instance->id}hidden"]));
239 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
240 'name' => "block{$blockmyprofile->instance->id}hidden"]));
241 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
242 'name' => "docked_block_instance_{$blockmyprofile->instance->id}"]));
243 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
244 'name' => "docked_block_instance_{$blockmentees->instance->id}"]));
245 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u2->id,
246 'name' => "docked_block_instance_{$blockmentees->instance->id}"]));
248 // Nothing happens.
249 provider::delete_data_for_all_users_in_context($c1ctx);
250 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
251 'name' => "block{$blocklogin->instance->id}hidden"]));
252 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u2->id,
253 'name' => "block{$blocklogin->instance->id}hidden"]));
254 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
255 'name' => "block{$blockprivatefiles->instance->id}hidden"]));
256 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
257 'name' => "block{$blockmyprofile->instance->id}hidden"]));
258 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
259 'name' => "docked_block_instance_{$blockmyprofile->instance->id}"]));
260 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
261 'name' => "docked_block_instance_{$blockmentees->instance->id}"]));
262 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u2->id,
263 'name' => "docked_block_instance_{$blockmentees->instance->id}"]));
265 // Delete one block.
266 provider::delete_data_for_all_users_in_context($blocklogin->context);
267 $this->assertFalse($DB->record_exists('user_preferences', ['userid' => $u1->id,
268 'name' => "block{$blocklogin->instance->id}hidden"]));
269 $this->assertFalse($DB->record_exists('user_preferences', ['userid' => $u2->id,
270 'name' => "block{$blocklogin->instance->id}hidden"]));
271 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
272 'name' => "block{$blockprivatefiles->instance->id}hidden"]));
273 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
274 'name' => "block{$blockmyprofile->instance->id}hidden"]));
275 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
276 'name' => "docked_block_instance_{$blockmyprofile->instance->id}"]));
277 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
278 'name' => "docked_block_instance_{$blockmentees->instance->id}"]));
279 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u2->id,
280 'name' => "docked_block_instance_{$blockmentees->instance->id}"]));
282 // Delete another block.
283 provider::delete_data_for_all_users_in_context($blockmyprofile->context);
284 $this->assertFalse($DB->record_exists('user_preferences', ['userid' => $u1->id,
285 'name' => "block{$blocklogin->instance->id}hidden"]));
286 $this->assertFalse($DB->record_exists('user_preferences', ['userid' => $u2->id,
287 'name' => "block{$blocklogin->instance->id}hidden"]));
288 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
289 'name' => "block{$blockprivatefiles->instance->id}hidden"]));
290 $this->assertFalse($DB->record_exists('user_preferences', ['userid' => $u1->id,
291 'name' => "block{$blockmyprofile->instance->id}hidden"]));
292 $this->assertFalse($DB->record_exists('user_preferences', ['userid' => $u1->id,
293 'name' => "docked_block_instance_{$blockmyprofile->instance->id}"]));
294 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u1->id,
295 'name' => "docked_block_instance_{$blockmentees->instance->id}"]));
296 $this->assertTrue($DB->record_exists('user_preferences', ['userid' => $u2->id,
297 'name' => "docked_block_instance_{$blockmentees->instance->id}"]));
301 * Test the deletion of data related to a context and a list of users.
303 public function test_delete_data_for_users() {
304 global $DB;
305 $u1 = $this->getDataGenerator()->create_user();
306 $u2 = $this->getDataGenerator()->create_user();
307 $u3 = $this->getDataGenerator()->create_user();
309 $course = $this->getDataGenerator()->create_course();
311 $manager = $this->get_block_manager(['region-a'], context_course::instance($course->id));
312 $manager->add_block('myprofile', 'region-a', 0, false);
313 $manager->load_blocks();
314 $blockmyprofile = $manager->get_blocks_for_region('region-a')[0];
316 $this->set_hidden_pref($blockmyprofile, true, $u1->id);
317 $this->set_hidden_pref($blockmyprofile, true, $u3->id);
318 $this->set_docked_pref($blockmyprofile, true, $u2->id);
319 $this->set_docked_pref($blockmyprofile, true, $u3->id);
321 $records = $DB->get_records('block_instances', ['blockname' => 'myprofile']);
322 $record = array_shift($records);
323 $blockcontext = context_block::instance($record->id);
325 $userlist = new \core_privacy\local\request\userlist($blockcontext, 'core_block');
326 provider::get_users_in_context($userlist);
327 $this->assertCount(3, $userlist->get_userids());
329 // Delete preferences for user 1 and 3 for the my profile block.
330 $userlist = new \core_privacy\local\request\approved_userlist($blockcontext, 'core_block', [$u1->id, $u3->id]);
331 provider::delete_data_for_users($userlist);
333 // Only user 2's preference is left.
334 $this->assertCount(1, $DB->get_records('user_preferences',
335 ['name' => "docked_block_instance_{$blockcontext->instanceid}"]));
336 // All of these are gone.
337 $this->assertEmpty($DB->get_records('user_preferences',
338 ['name' => "block{$blockcontext->instanceid}hidden"]));
341 public function test_export_data_for_user() {
342 global $DB;
343 $dg = $this->getDataGenerator();
344 $c1 = $dg->create_course();
345 $c2 = $dg->create_course();
346 $u1 = $dg->create_user();
347 $u2 = $dg->create_user();
348 $c1ctx = context_course::instance($c1->id);
349 $c2ctx = context_course::instance($c2->id);
350 $u1ctx = context_user::instance($u1->id);
351 $u2ctx = context_user::instance($u2->id);
352 $yes = transform::yesno(true);
353 $no = transform::yesno(false);
355 $manager = $this->get_block_manager(['region-a'], $c1ctx);
356 $manager->add_block('myprofile', 'region-a', 0, false);
357 $manager->add_block('login', 'region-a', 1, false);
358 $manager->add_block('mentees', 'region-a', 2, false);
359 $manager->add_block('private_files', 'region-a', 3, false);
360 $manager->load_blocks();
361 list($bmyprofile, $blogin, $bmentees, $bprivatefiles) = $manager->get_blocks_for_region('region-a');
363 // Set some user preferences.
364 $this->set_hidden_pref($blogin, true, $u1->id);
365 $this->set_docked_pref($blogin, false, $u1->id);
366 $this->set_docked_pref($blogin, true, $u2->id);
367 $this->set_hidden_pref($bprivatefiles, false, $u1->id);
368 $this->set_docked_pref($bprivatefiles, true, $u2->id);
369 $this->set_docked_pref($bmyprofile, true, $u1->id);
370 $this->set_docked_pref($bmentees, true, $u2->id);
372 // Export data.
373 provider::export_user_data(new approved_contextlist($u1, 'core_block', [$bmyprofile->context->id, $blogin->context->id,
374 $bmentees->context->id, $bprivatefiles->context->id]));
375 $prefs = writer::with_context($bmentees->context)->get_user_context_preferences('core_block');
376 $this->assertEmpty((array) $prefs);
378 $prefs = writer::with_context($blogin->context)->get_user_context_preferences('core_block');
379 $this->assertEquals($no, $prefs->block_is_docked->value);
380 $this->assertEquals($yes, $prefs->block_is_hidden->value);
382 $prefs = writer::with_context($bprivatefiles->context)->get_user_context_preferences('core_block');
383 $this->assertObjectNotHasAttribute('block_is_docked', $prefs);
384 $this->assertEquals($no, $prefs->block_is_hidden->value);
386 $prefs = writer::with_context($bmyprofile->context)->get_user_context_preferences('core_block');
387 $this->assertEquals($yes, $prefs->block_is_docked->value);
388 $this->assertObjectNotHasAttribute('block_is_hidden', $prefs);
392 * Get the block manager.
394 * @param array $regions The regions.
395 * @param context $context The context.
396 * @param string $pagetype The page type.
397 * @param string $subpage The sub page.
398 * @return block_manager
400 protected function get_block_manager($regions, $context, $pagetype = 'page-type', $subpage = '') {
401 $page = new moodle_page();
402 $page->set_context($context);
403 $page->set_pagetype($pagetype);
404 $page->set_subpage($subpage);
405 $page->set_url(new moodle_url('/'));
407 $blockmanager = new block_manager($page);
408 $blockmanager->add_regions($regions, false);
409 $blockmanager->set_default_region($regions[0]);
411 return $blockmanager;
415 * Set a docked preference.
417 * @param block_base $block The block.
418 * @param bool $value The value.
419 * @param int $userid The user ID.
421 protected function set_docked_pref($block, $value, $userid) {
422 set_user_preference("docked_block_instance_{$block->instance->id}", $value, $userid);
426 * Set a hidden preference.
428 * @param block_base $block The block.
429 * @param bool $value The value.
430 * @param int $userid The user ID.
432 protected function set_hidden_pref($block, $value, $userid) {
433 set_user_preference("block{$block->instance->id}hidden", $value, $userid);