See Release Notes
Long Term Support Release
Differences Between: [Versions 310 and 401] [Versions 311 and 401] [Versions 39 and 401]
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. 13 // 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/>. 16 17 namespace core_availability; 18 19 /** 20 * Unit tests for info and subclasses. 21 * 22 * @package core_availability 23 * @copyright 2014 The Open University 24 * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later 25 */ 26 class info_test extends \advanced_testcase { 27 public function setUp(): void { 28 // Load the mock condition so that it can be used. 29 require_once (__DIR__ . '/fixtures/mock_condition.php'); 30 } 31 32 /** 33 * Tests the info_module class (is_available, get_full_information). 34 */ 35 public function test_info_module() { 36 global $DB, $CFG; 37 38 // Create a course and pages. 39 $CFG->enableavailability = 0; 40 $this->setAdminUser(); 41 $this->resetAfterTest(); 42 $generator = $this->getDataGenerator(); 43 $course = $generator->create_course(); 44 $rec = array('course' => $course); 45 $page1 = $generator->get_plugin_generator('mod_page')->create_instance($rec); 46 $page2 = $generator->get_plugin_generator('mod_page')->create_instance($rec); 47 $page3 = $generator->get_plugin_generator('mod_page')->create_instance($rec); 48 $page4 = $generator->get_plugin_generator('mod_page')->create_instance($rec); 49 50 // Set up the availability option for the pages to mock options. 51 $DB->set_field('course_modules', 'availability', '{"op":"|","show":true,"c":[' . 52 '{"type":"mock","a":false,"m":"grandmaster flash"}]}', array('id' => $page1->cmid)); 53 $DB->set_field('course_modules', 'availability', '{"op":"|","show":true,"c":[' . 54 '{"type":"mock","a":true,"m":"the furious five"}]}', array('id' => $page2->cmid)); 55 56 // Third page is invalid. (Fourth has no availability settings.) 57 $DB->set_field('course_modules', 'availability', '{{{', array('id' => $page3->cmid)); 58 59 $modinfo = get_fast_modinfo($course); 60 $cm1 = $modinfo->get_cm($page1->cmid); 61 $cm2 = $modinfo->get_cm($page2->cmid); 62 $cm3 = $modinfo->get_cm($page3->cmid); 63 $cm4 = $modinfo->get_cm($page4->cmid); 64 65 // Do availability and full information checks. 66 $info = new info_module($cm1); 67 $information = ''; 68 $this->assertFalse($info->is_available($information)); 69 $this->assertEquals('SA: grandmaster flash', $information); 70 $this->assertEquals('SA: [FULL]grandmaster flash', $info->get_full_information()); 71 $info = new info_module($cm2); 72 $this->assertTrue($info->is_available($information)); 73 $this->assertEquals('', $information); 74 $this->assertEquals('SA: [FULL]the furious five', $info->get_full_information()); 75 76 // Check invalid one. 77 $info = new info_module($cm3); 78 $this->assertFalse($info->is_available($information)); 79 $debugging = $this->getDebuggingMessages(); 80 $this->resetDebugging(); 81 $this->assertEquals(1, count($debugging)); 82 $this->assertStringContainsString('Invalid availability', $debugging[0]->message); 83 84 // Check empty one. 85 $info = new info_module($cm4); 86 $this->assertTrue($info->is_available($information)); 87 $this->assertEquals('', $information); 88 $this->assertEquals('', $info->get_full_information()); 89 } 90 91 /** 92 * Tests the info_section class (is_available, get_full_information). 93 */ 94 public function test_info_section() { 95 global $DB; 96 97 // Create a course. 98 $this->setAdminUser(); 99 $this->resetAfterTest(); 100 $generator = $this->getDataGenerator(); 101 $course = $generator->create_course( 102 array('numsections' => 4), array('createsections' => true)); 103 104 // Set up the availability option for the sections to mock options. 105 $DB->set_field('course_sections', 'availability', '{"op":"|","show":true,"c":[' . 106 '{"type":"mock","a":false,"m":"public"}]}', 107 array('course' => $course->id, 'section' => 1)); 108 $DB->set_field('course_sections', 'availability', '{"op":"|","show":true,"c":[' . 109 '{"type":"mock","a":true,"m":"enemy"}]}', 110 array('course' => $course->id, 'section' => 2)); 111 112 // Third section is invalid. (Fourth has no availability setting.) 113 $DB->set_field('course_sections', 'availability', '{{{', 114 array('course' => $course->id, 'section' => 3)); 115 116 $modinfo = get_fast_modinfo($course); 117 $sections = $modinfo->get_section_info_all(); 118 119 // Do availability and full information checks. 120 $info = new info_section($sections[1]); 121 $information = ''; 122 $this->assertFalse($info->is_available($information)); 123 $this->assertEquals('SA: public', $information); 124 $this->assertEquals('SA: [FULL]public', $info->get_full_information()); 125 $info = new info_section($sections[2]); 126 $this->assertTrue($info->is_available($information)); 127 $this->assertEquals('', $information); 128 $this->assertEquals('SA: [FULL]enemy', $info->get_full_information()); 129 130 // Check invalid one. 131 $info = new info_section($sections[3]); 132 $this->assertFalse($info->is_available($information)); 133 $debugging = $this->getDebuggingMessages(); 134 $this->resetDebugging(); 135 $this->assertEquals(1, count($debugging)); 136 $this->assertStringContainsString('Invalid availability', $debugging[0]->message); 137 138 // Check empty one. 139 $info = new info_section($sections[4]); 140 $this->assertTrue($info->is_available($information)); 141 $this->assertEquals('', $information); 142 $this->assertEquals('', $info->get_full_information()); 143 } 144 145 /** 146 * Tests the is_user_visible() static function in info_module. 147 */ 148 public function test_is_user_visible() { 149 global $CFG, $DB; 150 require_once($CFG->dirroot . '/course/lib.php'); 151 $this->resetAfterTest(); 152 $CFG->enableavailability = 0; 153 154 // Create a course and some pages: 155 // 0. Invisible due to visible=0. 156 // 1. Availability restriction (mock, set to fail). 157 // 2. Availability restriction on section (mock, set to fail). 158 // 3. Actually visible. 159 $generator = $this->getDataGenerator(); 160 $course = $generator->create_course( 161 array('numsections' => 1), array('createsections' => true)); 162 $rec = array('course' => $course, ); 163 $pages = array(); 164 $pagegen = $generator->get_plugin_generator('mod_page'); 165 $pages[0] = $pagegen->create_instance($rec, array('visible' => 0)); 166 $pages[1] = $pagegen->create_instance($rec); 167 $pages[2] = $pagegen->create_instance($rec); 168 $pages[3] = $pagegen->create_instance($rec); 169 $modinfo = get_fast_modinfo($course); 170 $section = $modinfo->get_section_info(1); 171 $cm = $modinfo->get_cm($pages[2]->cmid); 172 moveto_module($cm, $section); 173 174 // Set the availability restrictions in database. The enableavailability 175 // setting is off so these do not take effect yet. 176 $notavailable = '{"op":"|","show":true,"c":[{"type":"mock","a":false}]}'; 177 $DB->set_field('course_sections', 'availability', 178 $notavailable, array('id' => $section->id)); 179 $DB->set_field('course_modules', 'availability', 180 $notavailable, array('id' => $pages[1]->cmid)); 181 get_fast_modinfo($course, 0, true); 182 183 // Set up 4 users - a teacher and student plus somebody who isn't even 184 // on the course. Also going to use admin user and a spare student to 185 // avoid cache problems. 186 $roleids = $DB->get_records_menu('role', null, '', 'shortname, id'); 187 $teacher = $generator->create_user(); 188 $student = $generator->create_user(); 189 $student2 = $generator->create_user(); 190 $other = $generator->create_user(); 191 $admin = $DB->get_record('user', array('username' => 'admin')); 192 $generator->enrol_user($teacher->id, $course->id, $roleids['teacher']); 193 $generator->enrol_user($student->id, $course->id, $roleids['student']); 194 $generator->enrol_user($student2->id, $course->id, $roleids['student']); 195 196 // Basic case when availability disabled, for visible item. 197 $this->assertTrue(info_module::is_user_visible($pages[3]->cmid, $student->id, false)); 198 199 // Specifying as an object should not make any queries. 200 $cm = $DB->get_record('course_modules', array('id' => $pages[3]->cmid)); 201 $beforequeries = $DB->perf_get_queries(); 202 $this->assertTrue(info_module::is_user_visible($cm, $student->id, false)); 203 $this->assertEquals($beforequeries, $DB->perf_get_queries()); 204 205 // Specifying as cm_info for correct user should not make any more queries 206 // if we have already obtained dynamic data. 207 $modinfo = get_fast_modinfo($course, $student->id); 208 $cminfo = $modinfo->get_cm($cm->id); 209 // This will obtain dynamic data. 210 $name = $cminfo->name; 211 $beforequeries = $DB->perf_get_queries(); 212 $this->assertTrue(info_module::is_user_visible($cminfo, $student->id, false)); 213 $this->assertEquals($beforequeries, $DB->perf_get_queries()); 214 215 // Function does not care if you are in the course (unless $checkcourse). 216 $this->assertTrue(info_module::is_user_visible($cm, $other->id, false)); 217 218 // With $checkcourse, check for enrolled, not enrolled, and admin user. 219 $this->assertTrue(info_module::is_user_visible($cm, $student->id, true)); 220 $this->assertFalse(info_module::is_user_visible($cm, $other->id, true)); 221 $this->assertTrue(info_module::is_user_visible($cm, $admin->id, true)); 222 223 // With availability off, the student can access all except the 224 // visible=0 one. 225 $this->assertFalse(info_module::is_user_visible($pages[0]->cmid, $student->id, false)); 226 $this->assertTrue(info_module::is_user_visible($pages[1]->cmid, $student->id, false)); 227 $this->assertTrue(info_module::is_user_visible($pages[2]->cmid, $student->id, false)); 228 229 // Teacher and admin can even access the visible=0 one. 230 $this->assertTrue(info_module::is_user_visible($pages[0]->cmid, $teacher->id, false)); 231 $this->assertTrue(info_module::is_user_visible($pages[0]->cmid, $admin->id, false)); 232 233 // Now enable availability (and clear cache). 234 $CFG->enableavailability = true; 235 get_fast_modinfo($course, 0, true); 236 237 // Student cannot access the activity restricted by its own or by the 238 // section's availability. 239 $this->assertFalse(info_module::is_user_visible($pages[1]->cmid, $student->id, false)); 240 $this->assertFalse(info_module::is_user_visible($pages[2]->cmid, $student->id, false)); 241 } 242 243 /** 244 * Tests the convert_legacy_fields function used in restore. 245 */ 246 public function test_convert_legacy_fields() { 247 // Check with no availability conditions first. 248 $rec = (object)array('availablefrom' => 0, 'availableuntil' => 0, 249 'groupingid' => 7, 'showavailability' => 1); 250 $this->assertNull(info::convert_legacy_fields($rec, false)); 251 252 // Check same list for a section. 253 $this->assertEquals( 254 '{"op":"&","showc":[false],"c":[{"type":"grouping","id":7}]}', 255 info::convert_legacy_fields($rec, true)); 256 257 // Check groupmembersonly with grouping. 258 $rec->groupmembersonly = 1; 259 $this->assertEquals( 260 '{"op":"&","showc":[false],"c":[{"type":"grouping","id":7}]}', 261 info::convert_legacy_fields($rec, false)); 262 263 // Check groupmembersonly without grouping. 264 $rec->groupingid = 0; 265 $this->assertEquals( 266 '{"op":"&","showc":[false],"c":[{"type":"group"}]}', 267 info::convert_legacy_fields($rec, false)); 268 269 // Check start date. 270 $rec->groupmembersonly = 0; 271 $rec->availablefrom = 123; 272 $this->assertEquals( 273 '{"op":"&","showc":[true],"c":[{"type":"date","d":">=","t":123}]}', 274 info::convert_legacy_fields($rec, false)); 275 276 // Start date with show = false. 277 $rec->showavailability = 0; 278 $this->assertEquals( 279 '{"op":"&","showc":[false],"c":[{"type":"date","d":">=","t":123}]}', 280 info::convert_legacy_fields($rec, false)); 281 282 // End date. 283 $rec->showavailability = 1; 284 $rec->availablefrom = 0; 285 $rec->availableuntil = 456; 286 $this->assertEquals( 287 '{"op":"&","showc":[false],"c":[{"type":"date","d":"<","t":456}]}', 288 info::convert_legacy_fields($rec, false)); 289 290 // All together now. 291 $rec->groupingid = 7; 292 $rec->groupmembersonly = 1; 293 $rec->availablefrom = 123; 294 $this->assertEquals( 295 '{"op":"&","showc":[false,true,false],"c":[' . 296 '{"type":"grouping","id":7},' . 297 '{"type":"date","d":">=","t":123},' . 298 '{"type":"date","d":"<","t":456}' . 299 ']}', 300 info::convert_legacy_fields($rec, false)); 301 $this->assertEquals( 302 '{"op":"&","showc":[false,true,false],"c":[' . 303 '{"type":"grouping","id":7},' . 304 '{"type":"date","d":">=","t":123},' . 305 '{"type":"date","d":"<","t":456}' . 306 ']}', 307 info::convert_legacy_fields($rec, false, true)); 308 } 309 310 /** 311 * Tests the add_legacy_availability_condition function used in restore. 312 */ 313 public function test_add_legacy_availability_condition() { 314 // Completion condition tests. 315 $rec = (object)array('sourcecmid' => 7, 'requiredcompletion' => 1); 316 // No previous availability, show = true. 317 $this->assertEquals( 318 '{"op":"&","showc":[true],"c":[{"type":"completion","cm":7,"e":1}]}', 319 info::add_legacy_availability_condition(null, $rec, true)); 320 // No previous availability, show = false. 321 $this->assertEquals( 322 '{"op":"&","showc":[false],"c":[{"type":"completion","cm":7,"e":1}]}', 323 info::add_legacy_availability_condition(null, $rec, false)); 324 325 // Existing availability. 326 $before = '{"op":"&","showc":[true],"c":[{"type":"date","d":">=","t":70}]}'; 327 $this->assertEquals( 328 '{"op":"&","showc":[true,true],"c":['. 329 '{"type":"date","d":">=","t":70},' . 330 '{"type":"completion","cm":7,"e":1}' . 331 ']}', 332 info::add_legacy_availability_condition($before, $rec, true)); 333 334 // Grade condition tests. 335 $rec = (object)array('gradeitemid' => 3, 'grademin' => 7, 'grademax' => null); 336 $this->assertEquals( 337 '{"op":"&","showc":[true],"c":[{"type":"grade","id":3,"min":7.00000}]}', 338 info::add_legacy_availability_condition(null, $rec, true)); 339 $rec->grademax = 8; 340 $this->assertEquals( 341 '{"op":"&","showc":[true],"c":[{"type":"grade","id":3,"min":7.00000,"max":8.00000}]}', 342 info::add_legacy_availability_condition(null, $rec, true)); 343 unset($rec->grademax); 344 unset($rec->grademin); 345 $this->assertEquals( 346 '{"op":"&","showc":[true],"c":[{"type":"grade","id":3}]}', 347 info::add_legacy_availability_condition(null, $rec, true)); 348 349 // Note: There is no need to test the grade condition with show 350 // true/false and existing availability, because this uses the same 351 // function. 352 } 353 354 /** 355 * Tests the add_legacy_availability_field_condition function used in restore. 356 */ 357 public function test_add_legacy_availability_field_condition() { 358 // User field, normal operator. 359 $rec = (object)array('userfield' => 'email', 'shortname' => null, 360 'operator' => 'contains', 'value' => '@'); 361 $this->assertEquals( 362 '{"op":"&","showc":[true],"c":[' . 363 '{"type":"profile","op":"contains","sf":"email","v":"@"}]}', 364 info::add_legacy_availability_field_condition(null, $rec, true)); 365 366 // User field, non-value operator. 367 $rec = (object)array('userfield' => 'email', 'shortname' => null, 368 'operator' => 'isempty', 'value' => ''); 369 $this->assertEquals( 370 '{"op":"&","showc":[true],"c":[' . 371 '{"type":"profile","op":"isempty","sf":"email"}]}', 372 info::add_legacy_availability_field_condition(null, $rec, true)); 373 374 // Custom field. 375 $rec = (object)array('userfield' => null, 'shortname' => 'frogtype', 376 'operator' => 'isempty', 'value' => ''); 377 $this->assertEquals( 378 '{"op":"&","showc":[true],"c":[' . 379 '{"type":"profile","op":"isempty","cf":"frogtype"}]}', 380 info::add_legacy_availability_field_condition(null, $rec, true)); 381 } 382 383 /** 384 * Tests the filter_user_list() and get_user_list_sql() functions. 385 */ 386 public function test_filter_user_list() { 387 global $CFG, $DB; 388 require_once($CFG->dirroot . '/course/lib.php'); 389 $this->resetAfterTest(); 390 $CFG->enableavailability = true; 391 392 // Create a course with 2 sections and 2 pages and 3 users. 393 // Availability is set up initially on the 'page/section 2' items. 394 $generator = $this->getDataGenerator(); 395 $course = $generator->create_course( 396 array('numsections' => 2), array('createsections' => true)); 397 $u1 = $generator->create_user(); 398 $u2 = $generator->create_user(); 399 $u3 = $generator->create_user(); 400 $studentroleid = $DB->get_field('role', 'id', array('shortname' => 'student'), MUST_EXIST); 401 $allusers = array($u1->id => $u1, $u2->id => $u2, $u3->id => $u3); 402 $generator->enrol_user($u1->id, $course->id, $studentroleid); 403 $generator->enrol_user($u2->id, $course->id, $studentroleid); 404 $generator->enrol_user($u3->id, $course->id, $studentroleid); 405 406 // Page 2 allows access to users 2 and 3, while section 2 allows access 407 // to users 1 and 2. 408 $pagegen = $generator->get_plugin_generator('mod_page'); 409 $page = $pagegen->create_instance(array('course' => $course)); 410 $page2 = $pagegen->create_instance(array('course' => $course, 411 'availability' => '{"op":"|","show":true,"c":[{"type":"mock","filter":[' . 412 $u2->id . ',' . $u3->id . ']}]}')); 413 $modinfo = get_fast_modinfo($course); 414 $section = $modinfo->get_section_info(1); 415 $section2 = $modinfo->get_section_info(2); 416 $DB->set_field('course_sections', 'availability', 417 '{"op":"|","show":true,"c":[{"type":"mock","filter":[' . $u1->id . ',' . $u2->id .']}]}', 418 array('id' => $section2->id)); 419 moveto_module($modinfo->get_cm($page2->cmid), $section2); 420 421 // With no restrictions, returns full list. 422 $info = new info_module($modinfo->get_cm($page->cmid)); 423 $this->assertEquals(array($u1->id, $u2->id, $u3->id), 424 array_keys($info->filter_user_list($allusers))); 425 $this->assertEquals(array('', array()), $info->get_user_list_sql(true)); 426 427 // Set an availability restriction in database for section 1. 428 // For the section we set it so it doesn't support filters; for the 429 // module we have a filter. 430 $DB->set_field('course_sections', 'availability', 431 '{"op":"|","show":true,"c":[{"type":"mock","a":false}]}', 432 array('id' => $section->id)); 433 $DB->set_field('course_modules', 'availability', 434 '{"op":"|","show":true,"c":[{"type":"mock","filter":[' . $u3->id .']}]}', 435 array('id' => $page->cmid)); 436 rebuild_course_cache($course->id, true); 437 $modinfo = get_fast_modinfo($course); 438 439 // Now it should work (for the module). 440 $info = new info_module($modinfo->get_cm($page->cmid)); 441 $expected = array($u3->id); 442 $this->assertEquals($expected, 443 array_keys($info->filter_user_list($allusers))); 444 list ($sql, $params) = $info->get_user_list_sql(); 445 $result = $DB->get_fieldset_sql($sql, $params); 446 sort($result); 447 $this->assertEquals($expected, $result); 448 $info = new info_section($modinfo->get_section_info(1)); 449 $this->assertEquals(array($u1->id, $u2->id, $u3->id), 450 array_keys($info->filter_user_list($allusers))); 451 $this->assertEquals(array('', array()), $info->get_user_list_sql(true)); 452 453 // With availability disabled, module returns full list too. 454 $CFG->enableavailability = false; 455 $info = new info_module($modinfo->get_cm($page->cmid)); 456 $this->assertEquals(array($u1->id, $u2->id, $u3->id), 457 array_keys($info->filter_user_list($allusers))); 458 $this->assertEquals(array('', array()), $info->get_user_list_sql(true)); 459 460 // Check the other section... 461 $CFG->enableavailability = true; 462 $info = new info_section($modinfo->get_section_info(2)); 463 $expected = array($u1->id, $u2->id); 464 $this->assertEquals($expected, array_keys($info->filter_user_list($allusers))); 465 list ($sql, $params) = $info->get_user_list_sql(true); 466 $result = $DB->get_fieldset_sql($sql, $params); 467 sort($result); 468 $this->assertEquals($expected, $result); 469 470 // And the module in that section - which has combined the section and 471 // module restrictions. 472 $info = new info_module($modinfo->get_cm($page2->cmid)); 473 $expected = array($u2->id); 474 $this->assertEquals($expected, array_keys($info->filter_user_list($allusers))); 475 list ($sql, $params) = $info->get_user_list_sql(true); 476 $result = $DB->get_fieldset_sql($sql, $params); 477 sort($result); 478 $this->assertEquals($expected, $result); 479 480 // If the students have viewhiddenactivities, they get past the module 481 // restriction. 482 role_change_permission($studentroleid, \context_module::instance($page2->cmid), 483 'moodle/course:ignoreavailabilityrestrictions', CAP_ALLOW); 484 $expected = array($u1->id, $u2->id); 485 $this->assertEquals($expected, array_keys($info->filter_user_list($allusers))); 486 list ($sql, $params) = $info->get_user_list_sql(true); 487 $result = $DB->get_fieldset_sql($sql, $params); 488 sort($result); 489 $this->assertEquals($expected, $result); 490 491 // If they have viewhiddensections, they also get past the section 492 // restriction. 493 role_change_permission($studentroleid, \context_course::instance($course->id), 494 'moodle/course:ignoreavailabilityrestrictions', CAP_ALLOW); 495 $expected = array($u1->id, $u2->id, $u3->id); 496 $this->assertEquals($expected, array_keys($info->filter_user_list($allusers))); 497 list ($sql, $params) = $info->get_user_list_sql(true); 498 $result = $DB->get_fieldset_sql($sql, $params); 499 sort($result); 500 $this->assertEquals($expected, $result); 501 } 502 503 /** 504 * Tests the info_module class when involved in a recursive call to $cm->name. 505 */ 506 public function test_info_recursive_name_call() { 507 global $DB; 508 509 $this->resetAfterTest(); 510 511 // Create a course and page. 512 $generator = $this->getDataGenerator(); 513 $course = $generator->create_course(); 514 $page1 = $generator->create_module('page', ['course' => $course->id, 'name' => 'Page1']); 515 516 // Set invalid availability. 517 $DB->set_field('course_modules', 'availability', 'not valid', ['id' => $page1->cmid]); 518 519 // Get the cm_info object. 520 $this->setAdminUser(); 521 $modinfo = get_fast_modinfo($course); 522 $cm1 = $modinfo->get_cm($page1->cmid); 523 524 // At this point we will generate dynamic data for $cm1, which will cause the debugging 525 // call below. 526 $this->assertEquals('Page1', $cm1->name); 527 528 $this->assertDebuggingCalled('Error processing availability data for ' . 529 '‘Page1’: Invalid availability text'); 530 } 531 532 /** 533 * Test for the is_available_for_all() method of the info base class. 534 * @covers \core_availability\info_module::is_available_for_all 535 */ 536 public function test_is_available_for_all() { 537 global $CFG, $DB; 538 $this->resetAfterTest(); 539 $CFG->enableavailability = 0; 540 541 $generator = $this->getDataGenerator(); 542 $course = $generator->create_course(); 543 $page = $generator->get_plugin_generator('mod_page')->create_instance(['course' => $course]); 544 545 // Set an availability restriction and reset the modinfo cache. 546 // The enableavailability setting is disabled so this does not take effect yet. 547 $notavailable = '{"op":"|","show":true,"c":[{"type":"mock","a":false}]}'; 548 $DB->set_field('course_modules', 'availability', $notavailable, ['id' => $page->cmid]); 549 get_fast_modinfo($course, 0, true); 550 551 // Availability is disabled, so we expect this module to be available for everyone. 552 $modinfo = get_fast_modinfo($course); 553 $info = new info_module($modinfo->get_cm($page->cmid)); 554 $this->assertTrue($info->is_available_for_all()); 555 556 // Now, enable availability restrictions, and check again. 557 // This time, we expect it to return false, because of the access restriction. 558 $CFG->enableavailability = 1; 559 $this->assertFalse($info->is_available_for_all()); 560 } 561 }
title
Description
Body
title
Description
Body
title
Description
Body
title
Body