Proyectos de Subversion Moodle

Rev

Rev 11 | | Comparar con el anterior | Ultima modificación | Ver Log |

Rev Autor Línea Nro. Línea
1 efrain 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 mod_wiki;
18
 
19
use core_external\external_api;
20
use externallib_advanced_testcase;
21
use mod_wiki_external;
22
 
23
defined('MOODLE_INTERNAL') || die();
24
 
25
global $CFG;
26
 
27
require_once($CFG->dirroot . '/webservice/tests/helpers.php');
28
require_once($CFG->dirroot . '/mod/wiki/lib.php');
29
 
30
/**
31
 * Wiki module external functions tests
32
 *
33
 * @package    mod_wiki
34
 * @category   external
35
 * @copyright  2015 Dani Palou <dani@moodle.com>
36
 * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
37
 * @since      Moodle 3.1
38
 */
1441 ariadna 39
final class externallib_test extends externallib_advanced_testcase {
1 efrain 40
 
41
    /** @var \stdClass course record. */
42
    protected $course;
43
 
44
    /** @var \stdClass activity record. */
45
    protected $wiki;
46
 
47
    /** @var \stdClass activity record. */
48
    protected $wikisep;
49
 
50
    /** @var \stdClass activity record. */
51
    protected $wikivis;
52
 
53
    /** @var \stdClass activity record. */
54
    protected $wikisepind;
55
 
56
    /** @var \stdClass activity record. */
57
    protected $wikivisind;
58
 
59
    /** @var \context_module context instance. */
60
    protected $context;
61
 
62
    /** @var \StdClass */
63
    protected $cm;
64
 
65
    /** @var \stdClass user record. */
66
    protected $student;
67
 
68
    /** @var \stdClass user record. */
69
    protected $student2;
70
 
71
    /** @var \stdClass user record. */
72
    protected $teacher;
73
 
74
    /** @var mixed a fieldset object, false or exception if error not found. */
75
    protected $studentrole;
76
 
77
    /** @var mixed a fieldset object, false or exception if error not found. */
78
    protected $teacherrole;
79
 
80
    /** @var \stdClass first page. */
81
    protected $firstpage;
82
 
83
    /** @var \stdClass group record */
84
    protected $group1;
85
 
86
    /** @var \stdClass group record */
87
    protected $group2;
88
 
89
    /** @var \stdClass first page. */
90
    protected $fpsepg1;
91
 
92
    /** @var \stdClass first page. */
93
    protected $fpsepg2;
94
 
95
    /** @var \stdClass first page. */
96
    protected $fpsepall;
97
 
98
    /** @var \stdClass first page. */
99
    protected $fpvisg1;
100
 
101
    /** @var \stdClass first page. */
102
    protected $fpvisg2;
103
 
104
    /** @var \stdClass first page. */
105
    protected $fpvisall;
106
 
107
    /** @var \stdClass first page. */
108
    protected $fpsepg1indt;
109
 
110
    /** @var \stdClass first page. */
111
    protected $fpsepg2indt;
112
 
113
    /** @var \stdClass first page. */
114
    protected $fpsepallindt;
115
 
116
    /** @var \stdClass first page. */
117
    protected $fpvisg1indt;
118
 
119
    /** @var \stdClass first page. */
120
    protected $fpvisg2indt;
121
 
122
    /** @var \stdClass first page. */
123
    protected $fpvisallindt;
124
 
125
    /** @var \stdClass first page. */
126
    protected $fpsepg1indstu;
127
 
128
    /** @var \stdClass first page. */
129
    protected $fpvisg1indstu;
130
 
131
    /** @var \stdClass first page. */
132
    protected $fpsepg1indstu2;
133
 
134
    /** @var \stdClass first page. */
135
    protected $fpvisg1indstu2;
136
 
137
    /** @var \stdClass user record. */
138
    protected $studentnotincourse;
139
 
140
    /** @var \stdClass course record. */
141
    protected $anothercourse;
142
 
143
    /** @var \stdClass group record. */
144
    protected $groupnotincourse;
145
 
146
    /**
147
     * Set up for every test
148
     */
149
    public function setUp(): void {
150
        global $DB;
1441 ariadna 151
        parent::setUp();
1 efrain 152
        $this->resetAfterTest();
153
        $this->setAdminUser();
154
 
155
        // Setup test data.
156
        $this->course = $this->getDataGenerator()->create_course();
157
        $this->wiki = $this->getDataGenerator()->create_module('wiki', array('course' => $this->course->id));
158
        $this->context = \context_module::instance($this->wiki->cmid);
159
        $this->cm = get_coursemodule_from_instance('wiki', $this->wiki->id);
160
 
161
        // Create users.
162
        $this->student = self::getDataGenerator()->create_user();
163
        $this->student2 = self::getDataGenerator()->create_user();
164
        $this->teacher = self::getDataGenerator()->create_user();
165
 
166
        // Users enrolments.
167
        $this->studentrole = $DB->get_record('role', array('shortname' => 'student'));
168
        $this->teacherrole = $DB->get_record('role', array('shortname' => 'editingteacher'));
169
        $this->getDataGenerator()->enrol_user($this->student->id, $this->course->id, $this->studentrole->id, 'manual');
170
        $this->getDataGenerator()->enrol_user($this->student2->id, $this->course->id, $this->studentrole->id, 'manual');
171
        $this->getDataGenerator()->enrol_user($this->teacher->id, $this->course->id, $this->teacherrole->id, 'manual');
172
 
173
        // Create first pages.
174
        $this->firstpage = $this->getDataGenerator()->get_plugin_generator('mod_wiki')->create_first_page($this->wiki,
175
            array('tags' => array('Cats', 'Dogs')));
176
    }
177
 
178
    /**
179
     * Create two collaborative wikis (separate/visible groups), 2 groups and a first page for each wiki and group.
180
     */
181
    private function create_collaborative_wikis_with_groups() {
182
        // Create groups and add student to one of them.
183
        if (!isset($this->group1)) {
184
            $this->group1 = $this->getDataGenerator()->create_group(array('courseid' => $this->course->id));
185
            $this->getDataGenerator()->create_group_member(array('userid' => $this->student->id, 'groupid' => $this->group1->id));
186
            $this->getDataGenerator()->create_group_member(array('userid' => $this->student2->id, 'groupid' => $this->group1->id));
187
        }
188
        if (!isset($this->group2)) {
189
            $this->group2 = $this->getDataGenerator()->create_group(array('courseid' => $this->course->id));
190
        }
191
 
192
        // Create two collaborative wikis.
193
        $this->wikisep = $this->getDataGenerator()->create_module('wiki',
194
                                                        array('course' => $this->course->id, 'groupmode' => SEPARATEGROUPS));
195
        $this->wikivis = $this->getDataGenerator()->create_module('wiki',
196
                                                        array('course' => $this->course->id, 'groupmode' => VISIBLEGROUPS));
197
 
198
        // Create pages.
199
        $wikigenerator = $this->getDataGenerator()->get_plugin_generator('mod_wiki');
200
        $this->fpsepg1 = $wikigenerator->create_first_page($this->wikisep, array('group' => $this->group1->id));
201
        $this->fpsepg2 = $wikigenerator->create_first_page($this->wikisep, array('group' => $this->group2->id));
202
        $this->fpsepall = $wikigenerator->create_first_page($this->wikisep, array('group' => 0)); // All participants.
203
        $this->fpvisg1 = $wikigenerator->create_first_page($this->wikivis, array('group' => $this->group1->id));
204
        $this->fpvisg2 = $wikigenerator->create_first_page($this->wikivis, array('group' => $this->group2->id));
205
        $this->fpvisall = $wikigenerator->create_first_page($this->wikivis, array('group' => 0)); // All participants.
206
    }
207
 
208
    /**
209
     * Create two individual wikis (separate/visible groups), 2 groups and a first page for each wiki and group.
210
     */
211
    private function create_individual_wikis_with_groups() {
212
        // Create groups and add student to one of them.
213
        if (!isset($this->group1)) {
214
            $this->group1 = $this->getDataGenerator()->create_group(array('courseid' => $this->course->id));
215
            $this->getDataGenerator()->create_group_member(array('userid' => $this->student->id, 'groupid' => $this->group1->id));
216
            $this->getDataGenerator()->create_group_member(array('userid' => $this->student2->id, 'groupid' => $this->group1->id));
217
        }
218
        if (!isset($this->group2)) {
219
            $this->group2 = $this->getDataGenerator()->create_group(array('courseid' => $this->course->id));
220
        }
221
 
222
        // Create two individual wikis.
223
        $this->wikisepind = $this->getDataGenerator()->create_module('wiki', array('course' => $this->course->id,
224
                                                        'groupmode' => SEPARATEGROUPS, 'wikimode' => 'individual'));
225
        $this->wikivisind = $this->getDataGenerator()->create_module('wiki', array('course' => $this->course->id,
226
                                                        'groupmode' => VISIBLEGROUPS, 'wikimode' => 'individual'));
227
 
228
        // Create pages. Student can only create pages in his groups.
229
        $wikigenerator = $this->getDataGenerator()->get_plugin_generator('mod_wiki');
230
        $this->setUser($this->teacher);
231
        $this->fpsepg1indt = $wikigenerator->create_first_page($this->wikisepind, array('group' => $this->group1->id));
232
        $this->fpsepg2indt = $wikigenerator->create_first_page($this->wikisepind, array('group' => $this->group2->id));
233
        $this->fpsepallindt = $wikigenerator->create_first_page($this->wikisepind, array('group' => 0)); // All participants.
234
        $this->fpvisg1indt = $wikigenerator->create_first_page($this->wikivisind, array('group' => $this->group1->id));
235
        $this->fpvisg2indt = $wikigenerator->create_first_page($this->wikivisind, array('group' => $this->group2->id));
236
        $this->fpvisallindt = $wikigenerator->create_first_page($this->wikivisind, array('group' => 0)); // All participants.
237
 
238
        $this->setUser($this->student);
239
        $this->fpsepg1indstu = $wikigenerator->create_first_page($this->wikisepind, array('group' => $this->group1->id));
240
        $this->fpvisg1indstu = $wikigenerator->create_first_page($this->wikivisind, array('group' => $this->group1->id));
241
 
242
        $this->setUser($this->student2);
243
        $this->fpsepg1indstu2 = $wikigenerator->create_first_page($this->wikisepind, array('group' => $this->group1->id));
244
        $this->fpvisg1indstu2 = $wikigenerator->create_first_page($this->wikivisind, array('group' => $this->group1->id));
245
 
246
    }
247
 
248
    /*
249
     * Test get wikis by courses
250
     */
11 efrain 251
    public function test_mod_wiki_get_wikis_by_courses(): void {
1 efrain 252
 
253
        // Create additional course.
254
        $course2 = self::getDataGenerator()->create_course();
255
 
256
        // Second wiki.
257
        $record = new \stdClass();
258
        $record->course = $course2->id;
259
        $wiki2 = self::getDataGenerator()->create_module('wiki', $record);
260
 
261
        // Execute real Moodle enrolment as we'll call unenrol() method on the instance later.
262
        $enrol = enrol_get_plugin('manual');
263
        $enrolinstances = enrol_get_instances($course2->id, true);
264
        foreach ($enrolinstances as $courseenrolinstance) {
265
            if ($courseenrolinstance->enrol == "manual") {
266
                $instance2 = $courseenrolinstance;
267
                break;
268
            }
269
        }
270
        $enrol->enrol_user($instance2, $this->student->id, $this->studentrole->id);
271
 
272
        self::setUser($this->student);
273
 
274
        $returndescription = mod_wiki_external::get_wikis_by_courses_returns();
275
 
276
        // Create what we expect to be returned when querying the two courses.
277
        // First for the student user.
278
        $expectedfields = array('id', 'coursemodule', 'course', 'name', 'intro', 'introformat', 'introfiles', 'lang',
279
                'firstpagetitle', 'wikimode', 'defaultformat', 'forceformat', 'editbegin', 'editend', 'section', 'visible',
280
                'groupmode', 'groupingid');
281
 
282
        // Add expected coursemodule and data.
283
        $wiki1 = $this->wiki;
284
        $wiki1->coursemodule = $wiki1->cmid;
285
        $wiki1->introformat = 1;
286
        $wiki1->section = 0;
287
        $wiki1->visible = true;
288
        $wiki1->groupmode = 0;
289
        $wiki1->groupingid = 0;
290
        $wiki1->introfiles = [];
291
        $wiki1->lang = '';
292
 
293
        $wiki2->coursemodule = $wiki2->cmid;
294
        $wiki2->introformat = 1;
295
        $wiki2->section = 0;
296
        $wiki2->visible = true;
297
        $wiki2->groupmode = 0;
298
        $wiki2->groupingid = 0;
299
        $wiki2->introfiles = [];
300
        $wiki2->lang = '';
301
 
302
        foreach ($expectedfields as $field) {
303
            $expected1[$field] = $wiki1->{$field};
304
            $expected2[$field] = $wiki2->{$field};
305
        }
306
        // Users can create pages by default.
307
        $expected1['cancreatepages'] = true;
308
        $expected2['cancreatepages'] = true;
309
 
310
        $expectedwikis = array($expected2, $expected1);
311
 
312
        // Call the external function passing course ids.
313
        $result = mod_wiki_external::get_wikis_by_courses(array($course2->id, $this->course->id));
314
        $result = external_api::clean_returnvalue($returndescription, $result);
315
 
316
        $this->assertEquals($expectedwikis, $result['wikis']);
317
        $this->assertCount(0, $result['warnings']);
318
 
319
        // Call the external function without passing course id.
320
        $result = mod_wiki_external::get_wikis_by_courses();
321
        $result = external_api::clean_returnvalue($returndescription, $result);
322
        $this->assertEquals($expectedwikis, $result['wikis']);
323
        $this->assertCount(0, $result['warnings']);
324
 
325
        // Unenrol user from second course and alter expected wikis.
326
        $enrol->unenrol_user($instance2, $this->student->id);
327
        array_shift($expectedwikis);
328
 
329
        // Call the external function without passing course id.
330
        $result = mod_wiki_external::get_wikis_by_courses();
331
        $result = external_api::clean_returnvalue($returndescription, $result);
332
        $this->assertEquals($expectedwikis, $result['wikis']);
333
 
334
        // Call for the second course we unenrolled the user from, expected warning.
335
        $result = mod_wiki_external::get_wikis_by_courses(array($course2->id));
336
        $this->assertCount(1, $result['warnings']);
337
        $this->assertEquals('1', $result['warnings'][0]['warningcode']);
338
        $this->assertEquals($course2->id, $result['warnings'][0]['itemid']);
339
 
340
        // Now, try as a teacher for getting all the additional fields.
341
        self::setUser($this->teacher);
342
 
343
        $additionalfields = array('timecreated', 'timemodified');
344
 
345
        foreach ($additionalfields as $field) {
346
            $expectedwikis[0][$field] = $wiki1->{$field};
347
        }
348
 
349
        $result = mod_wiki_external::get_wikis_by_courses();
350
        $result = external_api::clean_returnvalue($returndescription, $result);
351
        $this->assertEquals($expectedwikis, $result['wikis']);
352
 
353
        // Admin also should get all the information.
354
        self::setAdminUser();
355
 
356
        $result = mod_wiki_external::get_wikis_by_courses(array($this->course->id));
357
        $result = external_api::clean_returnvalue($returndescription, $result);
358
        $this->assertEquals($expectedwikis, $result['wikis']);
359
 
360
        // Now, prohibit capabilities.
361
        $this->setUser($this->student);
362
        $contextcourse1 = \context_course::instance($this->course->id);
363
 
364
        // Default student role allows to view wiki and create pages.
365
        $wikis = mod_wiki_external::get_wikis_by_courses(array($this->course->id));
366
        $wikis = external_api::clean_returnvalue(mod_wiki_external::get_wikis_by_courses_returns(), $wikis);
367
        $this->assertEquals('Test wiki 1', $wikis['wikis'][0]['intro']);
368
        $this->assertEquals(1, $wikis['wikis'][0]['cancreatepages']);
369
 
370
        // Prohibit capability = mod:wiki:viewpage on Course1 for students.
371
        assign_capability('mod/wiki:viewpage', CAP_PROHIBIT, $this->studentrole->id, $contextcourse1->id, true);
372
        accesslib_clear_all_caches_for_unit_testing();
373
        \course_modinfo::clear_instance_cache(null);
374
 
375
        $wikis = mod_wiki_external::get_wikis_by_courses(array($this->course->id));
376
        $wikis = external_api::clean_returnvalue(mod_wiki_external::get_wikis_by_courses_returns(), $wikis);
377
        $this->assertEquals(0, count($wikis['wikis']));
378
 
379
        // Prohibit capability = mod:wiki:createpage on Course1 for students.
380
        assign_capability('mod/wiki:viewpage', CAP_ALLOW, $this->studentrole->id, $contextcourse1->id, true);
381
        assign_capability('mod/wiki:createpage', CAP_PROHIBIT, $this->studentrole->id, $contextcourse1->id);
382
        accesslib_clear_all_caches_for_unit_testing();
383
        \course_modinfo::clear_instance_cache(null);
384
 
385
        $wikis = mod_wiki_external::get_wikis_by_courses(array($this->course->id));
386
        $wikis = external_api::clean_returnvalue(mod_wiki_external::get_wikis_by_courses_returns(), $wikis);
387
        $this->assertFalse($wikis['wikis'][0]['cancreatepages']);
388
 
389
    }
390
 
391
    /**
392
     * Test view_wiki.
393
     */
11 efrain 394
    public function test_view_wiki(): void {
1 efrain 395
 
396
        // Test invalid instance id.
397
        try {
398
            mod_wiki_external::view_wiki(0);
399
            $this->fail('Exception expected due to invalid mod_wiki instance id.');
400
        } catch (\moodle_exception $e) {
401
            $this->assertEquals('incorrectwikiid', $e->errorcode);
402
        }
403
 
404
        // Test not-enrolled user.
405
        $usernotenrolled = self::getDataGenerator()->create_user();
406
        $this->setUser($usernotenrolled);
407
        try {
408
            mod_wiki_external::view_wiki($this->wiki->id);
409
            $this->fail('Exception expected due to not enrolled user.');
410
        } catch (\moodle_exception $e) {
411
            $this->assertEquals('requireloginerror', $e->errorcode);
412
        }
413
 
414
        // Test user with full capabilities.
415
        $this->setUser($this->student);
416
 
417
        // Trigger and capture the event.
418
        $sink = $this->redirectEvents();
419
 
420
        $result = mod_wiki_external::view_wiki($this->wiki->id);
421
        $result = external_api::clean_returnvalue(mod_wiki_external::view_wiki_returns(), $result);
422
 
423
        $events = $sink->get_events();
424
        $this->assertCount(1, $events);
425
        $event = array_shift($events);
426
 
427
        // Checking that the event contains the expected values.
428
        $this->assertInstanceOf('\mod_wiki\event\course_module_viewed', $event);
429
        $this->assertEquals($this->context, $event->get_context());
430
        $moodlewiki = new \moodle_url('/mod/wiki/view.php', array('id' => $this->cm->id));
431
        $this->assertEquals($moodlewiki, $event->get_url());
432
        $this->assertEventContextNotUsed($event);
433
        $this->assertNotEmpty($event->get_name());
434
 
435
        // Test user with no capabilities.
436
        // We need a explicit prohibit since this capability is allowed for students by default.
437
        assign_capability('mod/wiki:viewpage', CAP_PROHIBIT, $this->studentrole->id, $this->context->id);
438
        accesslib_clear_all_caches_for_unit_testing();
439
 
440
        try {
441
            mod_wiki_external::view_wiki($this->wiki->id);
442
            $this->fail('Exception expected due to missing capability.');
443
        } catch (\moodle_exception $e) {
444
            $this->assertEquals('cannotviewpage', $e->errorcode);
445
        }
446
 
447
    }
448
 
449
    /**
450
     * Test view_page.
451
     */
11 efrain 452
    public function test_view_page(): void {
1 efrain 453
 
454
        // Test invalid page id.
455
        try {
456
            mod_wiki_external::view_page(0);
457
            $this->fail('Exception expected due to invalid view_page page id.');
458
        } catch (\moodle_exception $e) {
459
            $this->assertEquals('incorrectpageid', $e->errorcode);
460
        }
461
 
462
        // Test not-enrolled user.
463
        $usernotenrolled = self::getDataGenerator()->create_user();
464
        $this->setUser($usernotenrolled);
465
        try {
466
            mod_wiki_external::view_page($this->firstpage->id);
467
            $this->fail('Exception expected due to not enrolled user.');
468
        } catch (\moodle_exception $e) {
469
            $this->assertEquals('requireloginerror', $e->errorcode);
470
        }
471
 
472
        // Test user with full capabilities.
473
        $this->setUser($this->student);
474
 
475
        // Trigger and capture the event.
476
        $sink = $this->redirectEvents();
477
 
478
        $result = mod_wiki_external::view_page($this->firstpage->id);
479
        $result = external_api::clean_returnvalue(mod_wiki_external::view_page_returns(), $result);
480
 
481
        $events = $sink->get_events();
482
        $this->assertCount(1, $events);
483
        $event = array_shift($events);
484
 
485
        // Checking that the event contains the expected values.
486
        $this->assertInstanceOf('\mod_wiki\event\page_viewed', $event);
487
        $this->assertEquals($this->context, $event->get_context());
488
        $pageurl = new \moodle_url('/mod/wiki/view.php', array('pageid' => $this->firstpage->id));
489
        $this->assertEquals($pageurl, $event->get_url());
490
        $this->assertEventContextNotUsed($event);
491
        $this->assertNotEmpty($event->get_name());
492
 
493
        // Test user with no capabilities.
494
        // We need a explicit prohibit since this capability is allowed for students by default.
495
        assign_capability('mod/wiki:viewpage', CAP_PROHIBIT, $this->studentrole->id, $this->context->id);
496
        accesslib_clear_all_caches_for_unit_testing();
497
 
498
        try {
499
            mod_wiki_external::view_page($this->firstpage->id);
500
            $this->fail('Exception expected due to missing capability.');
501
        } catch (\moodle_exception $e) {
502
            $this->assertEquals('cannotviewpage', $e->errorcode);
503
        }
504
 
505
    }
506
 
507
    /**
508
     * Test get_subwikis.
509
     */
11 efrain 510
    public function test_get_subwikis(): void {
1 efrain 511
 
512
        // Test invalid wiki id.
513
        try {
514
            mod_wiki_external::get_subwikis(0);
515
            $this->fail('Exception expected due to invalid get_subwikis wiki id.');
516
        } catch (\moodle_exception $e) {
517
            $this->assertEquals('incorrectwikiid', $e->errorcode);
518
        }
519
 
520
        // Test not-enrolled user.
521
        $usernotenrolled = self::getDataGenerator()->create_user();
522
        $this->setUser($usernotenrolled);
523
        try {
524
            mod_wiki_external::get_subwikis($this->wiki->id);
525
            $this->fail('Exception expected due to not enrolled user.');
526
        } catch (\moodle_exception $e) {
527
            $this->assertEquals('requireloginerror', $e->errorcode);
528
        }
529
 
530
        // Test user with full capabilities.
531
        $this->setUser($this->student);
532
 
533
        // Create what we expect to be returned. We only test a basic case because deep testing is already done
534
        // in the tests for wiki_get_visible_subwikis.
535
        $expectedsubwikis = array();
536
        $expectedsubwiki = array(
537
                'id' => $this->firstpage->subwikiid,
538
                'wikiid' => $this->wiki->id,
539
                'groupid' => 0,
540
                'userid' => 0,
541
                'canedit' => true
542
            );
543
        $expectedsubwikis[] = $expectedsubwiki;
544
 
545
        $result = mod_wiki_external::get_subwikis($this->wiki->id);
546
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwikis_returns(), $result);
547
        $this->assertEquals($expectedsubwikis, $result['subwikis']);
548
        $this->assertCount(0, $result['warnings']);
549
 
550
        // Test user with no capabilities.
551
        // We need a explicit prohibit since this capability is allowed for students by default.
552
        assign_capability('mod/wiki:viewpage', CAP_PROHIBIT, $this->studentrole->id, $this->context->id);
553
        accesslib_clear_all_caches_for_unit_testing();
554
 
555
        try {
556
            mod_wiki_external::get_subwikis($this->wiki->id);
557
            $this->fail('Exception expected due to missing capability.');
558
        } catch (\moodle_exception $e) {
559
            $this->assertEquals('nopermissions', $e->errorcode);
560
        }
561
 
562
    }
563
 
564
    /**
565
     * Test get_subwiki_pages using an invalid wiki instance.
566
     */
11 efrain 567
    public function test_get_subwiki_pages_invalid_instance(): void {
1 efrain 568
        $this->expectException(\moodle_exception::class);
569
        mod_wiki_external::get_subwiki_pages(0);
570
    }
571
 
572
    /**
573
     * Test get_subwiki_pages using a user not enrolled in the course.
574
     */
11 efrain 575
    public function test_get_subwiki_pages_unenrolled_user(): void {
1 efrain 576
        // Create and use the user.
577
        $usernotenrolled = self::getDataGenerator()->create_user();
578
        $this->setUser($usernotenrolled);
579
 
580
        $this->expectException(\require_login_exception::class);
581
        mod_wiki_external::get_subwiki_pages($this->wiki->id);
582
    }
583
 
584
    /**
585
     * Test get_subwiki_pages using a hidden wiki as student.
586
     */
11 efrain 587
    public function test_get_subwiki_pages_hidden_wiki_as_student(): void {
1 efrain 588
        // Create a hidden wiki and try to get the list of pages.
589
        $hiddenwiki = $this->getDataGenerator()->create_module('wiki',
590
                            array('course' => $this->course->id, 'visible' => false));
591
 
592
        $this->setUser($this->student);
593
        $this->expectException(\require_login_exception::class);
594
        mod_wiki_external::get_subwiki_pages($hiddenwiki->id);
595
    }
596
 
597
    /**
598
     * Test get_subwiki_pages without the viewpage capability.
599
     */
11 efrain 600
    public function test_get_subwiki_pages_without_viewpage_capability(): void {
1 efrain 601
        // Prohibit capability = mod/wiki:viewpage on the course for students.
602
        $contextcourse = \context_course::instance($this->course->id);
603
        assign_capability('mod/wiki:viewpage', CAP_PROHIBIT, $this->studentrole->id, $contextcourse->id);
604
        accesslib_clear_all_caches_for_unit_testing();
605
 
606
        $this->setUser($this->student);
607
        $this->expectException(\moodle_exception::class);
608
        mod_wiki_external::get_subwiki_pages($this->wiki->id);
609
    }
610
 
611
    /**
612
     * Test get_subwiki_pages using an invalid userid.
613
     */
11 efrain 614
    public function test_get_subwiki_pages_invalid_userid(): void {
1 efrain 615
        // Create an individual wiki.
616
        $indwiki = $this->getDataGenerator()->create_module('wiki',
617
                                array('course' => $this->course->id, 'wikimode' => 'individual'));
618
 
619
        $this->expectException(\moodle_exception::class);
620
        mod_wiki_external::get_subwiki_pages($indwiki->id, 0, -10);
621
    }
622
 
623
    /**
624
     * Test get_subwiki_pages using an invalid groupid.
625
     */
11 efrain 626
    public function test_get_subwiki_pages_invalid_groupid(): void {
1 efrain 627
        // Create testing data.
628
        $this->create_collaborative_wikis_with_groups();
629
 
630
        $this->expectException(\moodle_exception::class);
631
        mod_wiki_external::get_subwiki_pages($this->wikisep->id, -111);
632
    }
633
 
634
    /**
635
     * Test get_subwiki_pages, check that a student can't see another user pages in an individual wiki without groups.
636
     */
11 efrain 637
    public function test_get_subwiki_pages_individual_student_see_other_user(): void {
1 efrain 638
        // Create an individual wiki.
639
        $indwiki = $this->getDataGenerator()->create_module('wiki',
640
                                array('course' => $this->course->id, 'wikimode' => 'individual'));
641
 
642
        $this->setUser($this->student);
643
        $this->expectException(\moodle_exception::class);
644
        mod_wiki_external::get_subwiki_pages($indwiki->id, 0, $this->teacher->id);
645
    }
646
 
647
    /**
648
     * Test get_subwiki_pages, check that a student can't get the pages from another group in
649
     * a collaborative wiki using separate groups.
650
     */
11 efrain 651
    public function test_get_subwiki_pages_collaborative_separate_groups_student_see_other_group(): void {
1 efrain 652
        // Create testing data.
653
        $this->create_collaborative_wikis_with_groups();
654
 
655
        $this->setUser($this->student);
656
        $this->expectException(\moodle_exception::class);
657
        mod_wiki_external::get_subwiki_pages($this->wikisep->id, $this->group2->id);
658
    }
659
 
660
    /**
661
     * Test get_subwiki_pages, check that a student can't get the pages from another group in
662
     * an individual wiki using separate groups.
663
     */
11 efrain 664
    public function test_get_subwiki_pages_individual_separate_groups_student_see_other_group(): void {
1 efrain 665
        // Create testing data.
666
        $this->create_individual_wikis_with_groups();
667
 
668
        $this->setUser($this->student);
669
        $this->expectException(\moodle_exception::class);
670
        mod_wiki_external::get_subwiki_pages($this->wikisepind->id, $this->group2->id, $this->teacher->id);
671
    }
672
 
673
    /**
674
     * Test get_subwiki_pages, check that a student can't get the pages from all participants in
675
     * a collaborative wiki using separate groups.
676
     */
11 efrain 677
    public function test_get_subwiki_pages_collaborative_separate_groups_student_see_all_participants(): void {
1 efrain 678
        // Create testing data.
679
        $this->create_collaborative_wikis_with_groups();
680
 
681
        $this->setUser($this->student);
682
        $this->expectException(\moodle_exception::class);
683
        mod_wiki_external::get_subwiki_pages($this->wikisep->id, 0);
684
    }
685
 
686
    /**
687
     * Test get_subwiki_pages, check that a student can't get the pages from all participants in
688
     * an individual wiki using separate groups.
689
     */
11 efrain 690
    public function test_get_subwiki_pages_individual_separate_groups_student_see_all_participants(): void {
1 efrain 691
        // Create testing data.
692
        $this->create_individual_wikis_with_groups();
693
 
694
        $this->setUser($this->student);
695
        $this->expectException(\moodle_exception::class);
696
        mod_wiki_external::get_subwiki_pages($this->wikisepind->id, 0, $this->teacher->id);
697
    }
698
 
699
    /**
700
     * Test get_subwiki_pages without groups and collaborative wiki.
701
     */
11 efrain 702
    public function test_get_subwiki_pages_collaborative(): void {
1 efrain 703
 
704
        // Test user with full capabilities.
705
        $this->setUser($this->student);
706
 
707
        // Set expected result: first page.
708
        $expectedpages = array();
709
        $expectedfirstpage = (array) $this->firstpage;
710
        $expectedfirstpage['caneditpage'] = true; // No groups and students have 'mod/wiki:editpage' capability.
711
        $expectedfirstpage['firstpage'] = true;
712
        $expectedfirstpage['contentformat'] = 1;
713
        $expectedfirstpage['tags'] = \core_tag\external\util::get_item_tags('mod_wiki', 'wiki_pages', $this->firstpage->id);
714
        // Cast to expected.
715
        $expectedfirstpage['tags'][0]['isstandard'] = (bool) $expectedfirstpage['tags'][0]['isstandard'];
716
        $expectedfirstpage['tags'][1]['isstandard'] = (bool) $expectedfirstpage['tags'][1]['isstandard'];
717
        $expectedpages[] = $expectedfirstpage;
718
 
719
        $result = mod_wiki_external::get_subwiki_pages($this->wiki->id);
720
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
721
        $this->assertEquals($expectedpages, $result['pages']);
722
 
723
        // Check that groupid param is ignored since the wiki isn't using groups.
724
        $result = mod_wiki_external::get_subwiki_pages($this->wiki->id, 1234);
725
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
726
        $this->assertEquals($expectedpages, $result['pages']);
727
 
728
        // Check that userid param is ignored since the wiki is collaborative.
729
        $result = mod_wiki_external::get_subwiki_pages($this->wiki->id, 1234, 1234);
730
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
731
        $this->assertEquals($expectedpages, $result['pages']);
732
 
733
        // Add a new page to the wiki and test again. We'll use a custom title so it's returned first if sorted by title.
734
        $newpage = $this->getDataGenerator()->get_plugin_generator('mod_wiki')->create_page(
735
                                $this->wiki, array('title' => 'AAA'));
736
 
737
        $expectednewpage = (array) $newpage;
738
        $expectednewpage['caneditpage'] = true; // No groups and students have 'mod/wiki:editpage' capability.
739
        $expectednewpage['firstpage'] = false;
740
        $expectednewpage['contentformat'] = 1;
741
        $expectednewpage['tags'] = array();
742
        array_unshift($expectedpages, $expectednewpage); // Add page to the beginning since it orders by title by default.
743
 
744
        $result = mod_wiki_external::get_subwiki_pages($this->wiki->id);
745
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
746
        $this->assertEquals($expectedpages, $result['pages']);
747
 
748
        // Now we'll order by ID. Since first page was created first it'll have a lower ID.
749
        $expectedpages = array($expectedfirstpage, $expectednewpage);
750
        $result = mod_wiki_external::get_subwiki_pages($this->wiki->id, 0, 0, array('sortby' => 'id'));
751
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
752
        $this->assertEquals($expectedpages, $result['pages']);
753
 
754
        // Check that WS doesn't return page content if includecontent is false, it returns the size instead.
755
        foreach ($expectedpages as $i => $expectedpage) {
756
            $expectedpages[$i]['contentsize'] = \core_text::strlen($expectedpages[$i]['cachedcontent']);
757
            unset($expectedpages[$i]['cachedcontent']);
758
            unset($expectedpages[$i]['contentformat']);
759
        }
760
        $result = mod_wiki_external::get_subwiki_pages($this->wiki->id, 0, 0, array('sortby' => 'id', 'includecontent' => 0));
761
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
762
        $this->assertEquals($expectedpages, $result['pages']);
763
    }
764
 
765
    /**
766
     * Test get_subwiki_pages without groups.
767
     */
11 efrain 768
    public function test_get_subwiki_pages_individual(): void {
1 efrain 769
 
770
        // Create an individual wiki to test userid param.
771
        $indwiki = $this->getDataGenerator()->create_module('wiki',
772
                                array('course' => $this->course->id, 'wikimode' => 'individual'));
773
 
774
        // Perform a request before creating any page to check that an empty array is returned if subwiki doesn't exist.
775
        $result = mod_wiki_external::get_subwiki_pages($indwiki->id);
776
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
777
        $this->assertEquals(array(), $result['pages']);
778
 
779
        // Create first pages as student and teacher.
780
        $this->setUser($this->student);
781
        $indfirstpagestudent = $this->getDataGenerator()->get_plugin_generator('mod_wiki')->create_first_page($indwiki);
782
        $this->setUser($this->teacher);
783
        $indfirstpageteacher = $this->getDataGenerator()->get_plugin_generator('mod_wiki')->create_first_page($indwiki);
784
 
785
        // Check that teacher can get his pages.
786
        $expectedteacherpage = (array) $indfirstpageteacher;
787
        $expectedteacherpage['caneditpage'] = true;
788
        $expectedteacherpage['firstpage'] = true;
789
        $expectedteacherpage['contentformat'] = 1;
790
        $expectedteacherpage['tags'] = array();
791
        $expectedpages = array($expectedteacherpage);
792
 
793
        $result = mod_wiki_external::get_subwiki_pages($indwiki->id, 0, $this->teacher->id);
794
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
795
        $this->assertEquals($expectedpages, $result['pages']);
796
 
797
        // Check that the teacher can see the student's pages.
798
        $expectedstudentpage = (array) $indfirstpagestudent;
799
        $expectedstudentpage['caneditpage'] = true;
800
        $expectedstudentpage['firstpage'] = true;
801
        $expectedstudentpage['contentformat'] = 1;
802
        $expectedstudentpage['tags'] = array();
803
        $expectedpages = array($expectedstudentpage);
804
 
805
        $result = mod_wiki_external::get_subwiki_pages($indwiki->id, 0, $this->student->id);
806
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
807
        $this->assertEquals($expectedpages, $result['pages']);
808
 
809
        // Now check that student can get his pages.
810
        $this->setUser($this->student);
811
 
812
        $result = mod_wiki_external::get_subwiki_pages($indwiki->id, 0, $this->student->id);
813
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
814
        $this->assertEquals($expectedpages, $result['pages']);
815
 
816
        // Check that not using userid uses current user.
817
        $result = mod_wiki_external::get_subwiki_pages($indwiki->id, 0);
818
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
819
        $this->assertEquals($expectedpages, $result['pages']);
820
    }
821
 
822
    /**
823
     * Test get_subwiki_pages with groups and collaborative wikis.
824
     */
11 efrain 825
    public function test_get_subwiki_pages_separate_groups_collaborative(): void {
1 efrain 826
 
827
        // Create testing data.
828
        $this->create_collaborative_wikis_with_groups();
829
 
830
        $this->setUser($this->student);
831
 
832
        // Try to get pages from a valid group in separate groups wiki.
833
 
834
        $expectedpage = (array) $this->fpsepg1;
835
        $expectedpage['caneditpage'] = true; // User belongs to group and has 'mod/wiki:editpage' capability.
836
        $expectedpage['firstpage'] = true;
837
        $expectedpage['contentformat'] = 1;
838
        $expectedpage['tags'] = array();
839
        $expectedpages = array($expectedpage);
840
 
841
        $result = mod_wiki_external::get_subwiki_pages($this->wikisep->id, $this->group1->id);
842
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
843
        $this->assertEquals($expectedpages, $result['pages']);
844
 
845
        // Let's check that not using groupid returns the same result (current group).
846
        $result = mod_wiki_external::get_subwiki_pages($this->wikisep->id);
847
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
848
        $this->assertEquals($expectedpages, $result['pages']);
849
 
850
        // Check that teacher can view a group pages without belonging to it.
851
        $this->setUser($this->teacher);
852
        $result = mod_wiki_external::get_subwiki_pages($this->wikisep->id, $this->group1->id);
853
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
854
        $this->assertEquals($expectedpages, $result['pages']);
855
 
856
        // Check that teacher can get the pages from all participants.
857
        $expectedpage = (array) $this->fpsepall;
858
        $expectedpage['caneditpage'] = true;
859
        $expectedpage['firstpage'] = true;
860
        $expectedpage['contentformat'] = 1;
861
        $expectedpage['tags'] = array();
862
        $expectedpages = array($expectedpage);
863
 
864
        $result = mod_wiki_external::get_subwiki_pages($this->wikisep->id, 0);
865
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
866
        $this->assertEquals($expectedpages, $result['pages']);
867
    }
868
 
869
    /**
870
     * Test get_subwiki_pages with groups and collaborative wikis.
871
     */
11 efrain 872
    public function test_get_subwiki_pages_visible_groups_collaborative(): void {
1 efrain 873
 
874
        // Create testing data.
875
        $this->create_collaborative_wikis_with_groups();
876
 
877
        $this->setUser($this->student);
878
 
879
        // Try to get pages from a valid group in visible groups wiki.
880
 
881
        $expectedpage = (array) $this->fpvisg1;
882
        $expectedpage['caneditpage'] = true; // User belongs to group and has 'mod/wiki:editpage' capability.
883
        $expectedpage['firstpage'] = true;
884
        $expectedpage['contentformat'] = 1;
885
        $expectedpage['tags'] = array();
886
        $expectedpages = array($expectedpage);
887
 
888
        $result = mod_wiki_external::get_subwiki_pages($this->wikivis->id, $this->group1->id);
889
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
890
        $this->assertEquals($expectedpages, $result['pages']);
891
 
892
        // Check that with visible groups a student can get the pages of groups he doesn't belong to.
893
        $expectedpage = (array) $this->fpvisg2;
894
        $expectedpage['caneditpage'] = false; // User doesn't belong to group so he can't edit the page.
895
        $expectedpage['firstpage'] = true;
896
        $expectedpage['contentformat'] = 1;
897
        $expectedpage['tags'] = array();
898
        $expectedpages = array($expectedpage);
899
 
900
        $result = mod_wiki_external::get_subwiki_pages($this->wikivis->id, $this->group2->id);
901
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
902
        $this->assertEquals($expectedpages, $result['pages']);
903
 
904
        // Check that with visible groups a student can get the pages of all participants.
905
        $expectedpage = (array) $this->fpvisall;
906
        $expectedpage['caneditpage'] = false;
907
        $expectedpage['firstpage'] = true;
908
        $expectedpage['contentformat'] = 1;
909
        $expectedpage['tags'] = array();
910
        $expectedpages = array($expectedpage);
911
 
912
        $result = mod_wiki_external::get_subwiki_pages($this->wikivis->id, 0);
913
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
914
        $this->assertEquals($expectedpages, $result['pages']);
915
    }
916
 
917
    /**
918
     * Test get_subwiki_pages with groups and individual wikis.
919
     */
11 efrain 920
    public function test_get_subwiki_pages_separate_groups_individual(): void {
1 efrain 921
 
922
        // Create testing data.
923
        $this->create_individual_wikis_with_groups();
924
 
925
        $this->setUser($this->student);
926
 
927
        // Check that student can retrieve his pages from separate wiki.
928
        $expectedpage = (array) $this->fpsepg1indstu;
929
        $expectedpage['caneditpage'] = true;
930
        $expectedpage['firstpage'] = true;
931
        $expectedpage['contentformat'] = 1;
932
        $expectedpage['tags'] = array();
933
        $expectedpages = array($expectedpage);
934
 
935
        $result = mod_wiki_external::get_subwiki_pages($this->wikisepind->id, $this->group1->id, $this->student->id);
936
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
937
        $this->assertEquals($expectedpages, $result['pages']);
938
 
939
        // Check that not using userid uses current user.
940
        $result = mod_wiki_external::get_subwiki_pages($this->wikisepind->id, $this->group1->id);
941
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
942
        $this->assertEquals($expectedpages, $result['pages']);
943
 
944
        // Check that the teacher can see the student pages.
945
        $this->setUser($this->teacher);
946
        $result = mod_wiki_external::get_subwiki_pages($this->wikisepind->id, $this->group1->id, $this->student->id);
947
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
948
        $this->assertEquals($expectedpages, $result['pages']);
949
 
950
        // Check that a student can see pages from another user that belongs to his groups.
951
        $this->setUser($this->student);
952
        $expectedpage = (array) $this->fpsepg1indstu2;
953
        $expectedpage['caneditpage'] = false;
954
        $expectedpage['firstpage'] = true;
955
        $expectedpage['contentformat'] = 1;
956
        $expectedpage['tags'] = array();
957
        $expectedpages = array($expectedpage);
958
 
959
        $result = mod_wiki_external::get_subwiki_pages($this->wikisepind->id, $this->group1->id, $this->student2->id);
960
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
961
        $this->assertEquals($expectedpages, $result['pages']);
962
    }
963
 
964
    /**
965
     * Test get_subwiki_pages with groups and individual wikis.
966
     */
11 efrain 967
    public function test_get_subwiki_pages_visible_groups_individual(): void {
1 efrain 968
 
969
        // Create testing data.
970
        $this->create_individual_wikis_with_groups();
971
 
972
        $this->setUser($this->student);
973
 
974
        // Check that student can retrieve his pages from visible wiki.
975
        $expectedpage = (array) $this->fpvisg1indstu;
976
        $expectedpage['caneditpage'] = true;
977
        $expectedpage['firstpage'] = true;
978
        $expectedpage['contentformat'] = 1;
979
        $expectedpage['tags'] = array();
980
        $expectedpages = array($expectedpage);
981
 
982
        $result = mod_wiki_external::get_subwiki_pages($this->wikivisind->id, $this->group1->id, $this->student->id);
983
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
984
        $this->assertEquals($expectedpages, $result['pages']);
985
 
986
        // Check that student can see teacher pages in visible groups, even if the user doesn't belong to the group.
987
        $expectedpage = (array) $this->fpvisg2indt;
988
        $expectedpage['caneditpage'] = false;
989
        $expectedpage['firstpage'] = true;
990
        $expectedpage['contentformat'] = 1;
991
        $expectedpage['tags'] = array();
992
        $expectedpages = array($expectedpage);
993
 
994
        $result = mod_wiki_external::get_subwiki_pages($this->wikivisind->id, $this->group2->id, $this->teacher->id);
995
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
996
        $this->assertEquals($expectedpages, $result['pages']);
997
 
998
        // Check that with visible groups a student can get the pages of all participants.
999
        $expectedpage = (array) $this->fpvisallindt;
1000
        $expectedpage['caneditpage'] = false;
1001
        $expectedpage['firstpage'] = true;
1002
        $expectedpage['contentformat'] = 1;
1003
        $expectedpage['tags'] = array();
1004
        $expectedpages = array($expectedpage);
1005
 
1006
        $result = mod_wiki_external::get_subwiki_pages($this->wikivisind->id, 0, $this->teacher->id);
1007
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_pages_returns(), $result);
1008
        $this->assertEquals($expectedpages, $result['pages']);
1009
    }
1010
 
1011
    /**
1012
     * Test get_page_contents using an invalid pageid.
1013
     */
11 efrain 1014
    public function test_get_page_contents_invalid_pageid(): void {
1 efrain 1015
        $this->expectException(\moodle_exception::class);
1016
        mod_wiki_external::get_page_contents(0);
1017
    }
1018
 
1019
    /**
1020
     * Test get_page_contents using a user not enrolled in the course.
1021
     */
11 efrain 1022
    public function test_get_page_contents_unenrolled_user(): void {
1 efrain 1023
        // Create and use the user.
1024
        $usernotenrolled = self::getDataGenerator()->create_user();
1025
        $this->setUser($usernotenrolled);
1026
 
1027
        $this->expectException(\require_login_exception::class);
1028
        mod_wiki_external::get_page_contents($this->firstpage->id);
1029
    }
1030
 
1031
    /**
1032
     * Test get_page_contents using a hidden wiki as student.
1033
     */
11 efrain 1034
    public function test_get_page_contents_hidden_wiki_as_student(): void {
1 efrain 1035
        // Create a hidden wiki and try to get a page contents.
1036
        $hiddenwiki = $this->getDataGenerator()->create_module('wiki',
1037
                            array('course' => $this->course->id, 'visible' => false));
1038
        $hiddenpage = $this->getDataGenerator()->get_plugin_generator('mod_wiki')->create_page($hiddenwiki);
1039
 
1040
        $this->setUser($this->student);
1041
        $this->expectException(\require_login_exception::class);
1042
        mod_wiki_external::get_page_contents($hiddenpage->id);
1043
    }
1044
 
1045
    /**
1046
     * Test get_page_contents without the viewpage capability.
1047
     */
11 efrain 1048
    public function test_get_page_contents_without_viewpage_capability(): void {
1 efrain 1049
        // Prohibit capability = mod/wiki:viewpage on the course for students.
1050
        $contextcourse = \context_course::instance($this->course->id);
1051
        assign_capability('mod/wiki:viewpage', CAP_PROHIBIT, $this->studentrole->id, $contextcourse->id);
1052
        accesslib_clear_all_caches_for_unit_testing();
1053
 
1054
        $this->setUser($this->student);
1055
        $this->expectException(\moodle_exception::class);
1056
        mod_wiki_external::get_page_contents($this->firstpage->id);
1057
    }
1058
 
1059
    /**
1060
     * Test get_page_contents, check that a student can't get a page from another group when
1061
     * using separate groups.
1062
     */
11 efrain 1063
    public function test_get_page_contents_separate_groups_student_see_other_group(): void {
1 efrain 1064
        // Create testing data.
1065
        $this->create_individual_wikis_with_groups();
1066
 
1067
        $this->setUser($this->student);
1068
        $this->expectException(\moodle_exception::class);
1069
        mod_wiki_external::get_page_contents($this->fpsepg2indt->id);
1070
    }
1071
 
1072
    /**
1073
     * Test get_page_contents without groups. We won't test all the possible cases because that's already
1074
     * done in the tests for get_subwiki_pages.
1075
     */
11 efrain 1076
    public function test_get_page_contents(): void {
1 efrain 1077
 
1078
        // Test user with full capabilities.
1079
        $this->setUser($this->student);
1080
 
1081
        // Set expected result: first page.
1082
        $expectedpage = array(
1083
            'id' => $this->firstpage->id,
1084
            'wikiid' => $this->wiki->id,
1085
            'subwikiid' => $this->firstpage->subwikiid,
1086
            'groupid' => 0, // No groups.
1087
            'userid' => 0, // Collaborative.
1088
            'title' => $this->firstpage->title,
1089
            'cachedcontent' => $this->firstpage->cachedcontent,
1090
            'contentformat' => 1,
1091
            'caneditpage' => true,
1092
            'version' => 1,
1093
            'tags' => \core_tag\external\util::get_item_tags('mod_wiki', 'wiki_pages', $this->firstpage->id),
1094
        );
1095
        // Cast to expected.
1096
        $expectedpage['tags'][0]['isstandard'] = (bool) $expectedpage['tags'][0]['isstandard'];
1097
        $expectedpage['tags'][1]['isstandard'] = (bool) $expectedpage['tags'][1]['isstandard'];
1098
 
1099
        $result = mod_wiki_external::get_page_contents($this->firstpage->id);
1100
        $result = external_api::clean_returnvalue(mod_wiki_external::get_page_contents_returns(), $result);
1101
        $this->assertEquals($expectedpage, $result['page']);
1102
 
1103
        // Add a new page to the wiki and test with it.
1104
        $newpage = $this->getDataGenerator()->get_plugin_generator('mod_wiki')->create_page($this->wiki);
1105
 
1106
        $expectedpage['id'] = $newpage->id;
1107
        $expectedpage['title'] = $newpage->title;
1108
        $expectedpage['cachedcontent'] = $newpage->cachedcontent;
1109
        $expectedpage['tags'] = array();
1110
 
1111
        $result = mod_wiki_external::get_page_contents($newpage->id);
1112
        $result = external_api::clean_returnvalue(mod_wiki_external::get_page_contents_returns(), $result);
1113
        $this->assertEquals($expectedpage, $result['page']);
1114
    }
1115
 
1116
    /**
1117
     * Test get_page_contents with groups. We won't test all the possible cases because that's already
1118
     * done in the tests for get_subwiki_pages.
1119
     */
11 efrain 1120
    public function test_get_page_contents_with_groups(): void {
1 efrain 1121
 
1122
        // Create testing data.
1123
        $this->create_individual_wikis_with_groups();
1124
 
1125
        // Try to get page from a valid group in separate groups wiki.
1126
        $this->setUser($this->student);
1127
 
1128
        $expectedfpsepg1indstu = array(
1129
            'id' => $this->fpsepg1indstu->id,
1130
            'wikiid' => $this->wikisepind->id,
1131
            'subwikiid' => $this->fpsepg1indstu->subwikiid,
1132
            'groupid' => $this->group1->id,
1133
            'userid' => $this->student->id,
1134
            'title' => $this->fpsepg1indstu->title,
1135
            'cachedcontent' => $this->fpsepg1indstu->cachedcontent,
1136
            'contentformat' => 1,
1137
            'caneditpage' => true,
1138
            'version' => 1,
1139
            'tags' => array(),
1140
        );
1141
 
1142
        $result = mod_wiki_external::get_page_contents($this->fpsepg1indstu->id);
1143
        $result = external_api::clean_returnvalue(mod_wiki_external::get_page_contents_returns(), $result);
1144
        $this->assertEquals($expectedfpsepg1indstu, $result['page']);
1145
 
1146
        // Check that teacher can view a group pages without belonging to it.
1147
        $this->setUser($this->teacher);
1148
        $result = mod_wiki_external::get_page_contents($this->fpsepg1indstu->id);
1149
        $result = external_api::clean_returnvalue(mod_wiki_external::get_page_contents_returns(), $result);
1150
        $this->assertEquals($expectedfpsepg1indstu, $result['page']);
1151
    }
1152
 
1153
    /**
1154
     * Test get_subwiki_files using a wiki without files.
1155
     */
11 efrain 1156
    public function test_get_subwiki_files_no_files(): void {
1 efrain 1157
        $result = mod_wiki_external::get_subwiki_files($this->wiki->id);
1158
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_files_returns(), $result);
1159
        $this->assertCount(0, $result['files']);
1160
        $this->assertCount(0, $result['warnings']);
1161
    }
1162
 
1163
    /**
1164
     * Test get_subwiki_files, check that a student can't get files from another group's subwiki when
1165
     * using separate groups.
1166
     */
11 efrain 1167
    public function test_get_subwiki_files_separate_groups_student_see_other_group(): void {
1 efrain 1168
        // Create testing data.
1169
        $this->create_collaborative_wikis_with_groups();
1170
 
1171
        $this->setUser($this->student);
1172
        $this->expectException(\moodle_exception::class);
1173
        mod_wiki_external::get_subwiki_files($this->wikisep->id, $this->group2->id);
1174
    }
1175
 
1176
    /**
1177
     * Test get_subwiki_files using a collaborative wiki without groups.
1178
     */
11 efrain 1179
    public function test_get_subwiki_files_collaborative_no_groups(): void {
1 efrain 1180
        $this->setUser($this->student);
1181
 
1182
        // Add a file as subwiki attachment.
1183
        $fs = get_file_storage();
1184
        $file = array('component' => 'mod_wiki', 'filearea' => 'attachments',
1185
                'contextid' => $this->context->id, 'itemid' => $this->firstpage->subwikiid,
1186
                'filename' => 'image.jpg', 'filepath' => '/', 'timemodified' => time());
1187
        $content = 'IMAGE';
1188
        $fs->create_file_from_string($file, $content);
1189
 
1190
        $expectedfile = array(
1191
            'filename' => $file['filename'],
1192
            'filepath' => $file['filepath'],
1193
            'mimetype' => 'image/jpeg',
1194
            'isexternalfile' => false,
1195
            'filesize' => strlen($content),
1196
            'timemodified' => $file['timemodified'],
1197
            'fileurl' => \moodle_url::make_webservice_pluginfile_url($file['contextid'], $file['component'],
1198
                            $file['filearea'], $file['itemid'], $file['filepath'], $file['filename']),
1199
            'icon' => 'f/image',
1200
        );
1201
 
1202
        // Call the WS and check that it returns this file.
1203
        $result = mod_wiki_external::get_subwiki_files($this->wiki->id);
1204
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_files_returns(), $result);
1205
        $this->assertCount(1, $result['files']);
1206
        $this->assertEquals($expectedfile, $result['files'][0]);
1207
 
1208
        // Now add another file to the same subwiki.
1209
        $file['filename'] = 'Another image.jpg';
1210
        $file['timemodified'] = time();
1211
        $content = 'ANOTHER IMAGE';
1212
        $fs->create_file_from_string($file, $content);
1213
 
1214
        $expectedfile['filename'] = $file['filename'];
1215
        $expectedfile['timemodified'] = $file['timemodified'];
1216
        $expectedfile['filesize'] = strlen($content);
1217
        $expectedfile['fileurl'] = \moodle_url::make_webservice_pluginfile_url($file['contextid'], $file['component'],
1218
                            $file['filearea'], $file['itemid'], $file['filepath'], $file['filename']);
1219
 
1220
        // Call the WS and check that it returns both files file.
1221
        $result = mod_wiki_external::get_subwiki_files($this->wiki->id);
1222
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_files_returns(), $result);
1223
        $this->assertCount(2, $result['files']);
1224
        // The new file is returned first because they're returned in alphabetical order.
1225
        $this->assertEquals($expectedfile, $result['files'][0]);
1226
    }
1227
 
1228
    /**
1229
     * Test get_subwiki_files using an individual wiki with visible groups.
1230
     */
11 efrain 1231
    public function test_get_subwiki_files_visible_groups_individual(): void {
1 efrain 1232
        // Create testing data.
1233
        $this->create_individual_wikis_with_groups();
1234
 
1235
        $this->setUser($this->student);
1236
 
1237
        // Add a file as subwiki attachment in the student group 1 subwiki.
1238
        $fs = get_file_storage();
1239
        $contextwiki = \context_module::instance($this->wikivisind->cmid);
1240
        $file = array('component' => 'mod_wiki', 'filearea' => 'attachments',
1241
                'contextid' => $contextwiki->id, 'itemid' => $this->fpvisg1indstu->subwikiid,
1242
                'filename' => 'image.jpg', 'filepath' => '/', 'timemodified' => time());
1243
        $content = 'IMAGE';
1244
        $fs->create_file_from_string($file, $content);
1245
 
1246
        $expectedfile = array(
1247
            'filename' => $file['filename'],
1248
            'filepath' => $file['filepath'],
1249
            'mimetype' => 'image/jpeg',
1250
            'isexternalfile' => false,
1251
            'filesize' => strlen($content),
1252
            'timemodified' => $file['timemodified'],
1253
            'fileurl' => \moodle_url::make_webservice_pluginfile_url($file['contextid'], $file['component'],
1254
                            $file['filearea'], $file['itemid'], $file['filepath'], $file['filename']),
1255
            'icon' => 'f/image',
1256
        );
1257
 
1258
        // Call the WS and check that it returns this file.
1259
        $result = mod_wiki_external::get_subwiki_files($this->wikivisind->id, $this->group1->id);
1260
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_files_returns(), $result);
1261
        $this->assertCount(1, $result['files']);
1262
        $this->assertEquals($expectedfile, $result['files'][0]);
1263
 
1264
        // Now check that a teacher can see it too.
1265
        $this->setUser($this->teacher);
1266
        $result = mod_wiki_external::get_subwiki_files($this->wikivisind->id, $this->group1->id, $this->student->id);
1267
        $result = external_api::clean_returnvalue(mod_wiki_external::get_subwiki_files_returns(), $result);
1268
        $this->assertCount(1, $result['files']);
1269
        $this->assertEquals($expectedfile, $result['files'][0]);
1270
    }
1271
 
1272
 
1273
    /**
1274
     * Test get_page_for_editing. We won't test all the possible cases because that's already
1275
     * done in the tests for wiki_parser_proxy::get_section.
1276
     */
11 efrain 1277
    public function test_get_page_for_editing(): void {
1 efrain 1278
 
1279
        $this->create_individual_wikis_with_groups();
1280
 
1281
        // We add a <span> in the first title to verify the WS works sending HTML in section.
1282
        $sectioncontent = '<h1><span>Title1</span></h1>Text inside section';
1283
        $pagecontent = $sectioncontent.'<h1>Title2</h1>Text inside section';
1284
        $newpage = $this->getDataGenerator()->get_plugin_generator('mod_wiki')->create_page(
1285
                                $this->wiki, array('content' => $pagecontent));
1286
 
1287
        // Test user with full capabilities.
1288
        $this->setUser($this->student);
1289
 
1290
        // Set expected result: Full Page content.
1291
        $expected = array(
1292
            'content' => $pagecontent,
1293
            'contentformat' => 'html',
1294
            'version' => '1'
1295
        );
1296
 
1297
        $result = mod_wiki_external::get_page_for_editing($newpage->id);
1298
        $result = external_api::clean_returnvalue(mod_wiki_external::get_page_for_editing_returns(), $result);
1299
        $this->assertEquals($expected, $result['pagesection']);
1300
 
1301
        // Set expected result: Section Page content.
1302
        $expected = array(
1303
            'content' => $sectioncontent,
1304
            'contentformat' => 'html',
1305
            'version' => '1'
1306
        );
1307
 
1308
        $result = mod_wiki_external::get_page_for_editing($newpage->id, '<span>Title1</span>');
1309
        $result = external_api::clean_returnvalue(mod_wiki_external::get_page_for_editing_returns(), $result);
1310
        $this->assertEquals($expected, $result['pagesection']);
1311
    }
1312
 
1313
    /**
1314
     * Test test_get_page_locking.
1315
     */
11 efrain 1316
    public function test_get_page_locking(): void {
1 efrain 1317
 
1318
        $this->create_individual_wikis_with_groups();
1319
 
1320
        $pagecontent = '<h1>Title1</h1>Text inside section<h1>Title2</h1>Text inside section';
1321
        $newpage = $this->getDataGenerator()->get_plugin_generator('mod_wiki')->create_page(
1322
                                $this->wiki, array('content' => $pagecontent));
1323
 
1324
        // Test user with full capabilities.
1325
        $this->setUser($this->student);
1326
 
1327
        // Test Section locking.
1328
        $expected = array(
1329
            'version' => '1'
1330
        );
1331
 
1332
        $result = mod_wiki_external::get_page_for_editing($newpage->id, 'Title1', true);
1333
        $result = external_api::clean_returnvalue(mod_wiki_external::get_page_for_editing_returns(), $result);
1334
        $this->assertEquals($expected, $result['pagesection']);
1335
 
1336
        // Test the section is locked.
1337
        $this->setUser($this->student2);
1338
        try {
1339
            mod_wiki_external::get_page_for_editing($newpage->id, 'Title1', true);
1340
            $this->fail('Exception expected due to not page locking.');
1341
        } catch (\moodle_exception $e) {
1342
            $this->assertEquals('pageislocked', $e->errorcode);
1343
        }
1344
 
1345
        // Test the page is locked.
1346
        try {
1347
            mod_wiki_external::get_page_for_editing($newpage->id, null, true);
1348
            $this->fail('Exception expected due to not page locking.');
1349
        } catch (\moodle_exception $e) {
1350
            $this->assertEquals('pageislocked', $e->errorcode);
1351
        }
1352
 
1353
        // Test the other section is not locked.
1354
        $result = mod_wiki_external::get_page_for_editing($newpage->id, 'Title2', true);
1355
        $result = external_api::clean_returnvalue(mod_wiki_external::get_page_for_editing_returns(), $result);
1356
        $this->assertEquals($expected, $result['pagesection']);
1357
 
1358
        // Back to the original user to test version change when editing.
1359
        $this->setUser($this->student);
1360
        $newsectioncontent = '<h1>Title2</h1>New test2';
1361
        $result = mod_wiki_external::edit_page($newpage->id, $newsectioncontent, 'Title1');
1362
 
1363
        $expected = array(
1364
            'version' => '2'
1365
        );
1366
        $result = mod_wiki_external::get_page_for_editing($newpage->id, 'Title1', true);
1367
        $result = external_api::clean_returnvalue(mod_wiki_external::get_page_for_editing_returns(), $result);
1368
        $this->assertEquals($expected, $result['pagesection']);
1369
    }
1370
 
1371
    /**
1372
     * Test new_page. We won't test all the possible cases because that's already
1373
     * done in the tests for wiki_create_page.
1374
     */
11 efrain 1375
    public function test_new_page(): void {
1 efrain 1376
 
1377
        $this->create_individual_wikis_with_groups();
1378
 
1379
        $sectioncontent = '<h1>Title1</h1>Text inside section';
1380
        $pagecontent = $sectioncontent.'<h1>Title2</h1>Text inside section';
1381
        $pagetitle = 'Page Title';
1382
 
1383
        // Test user with full capabilities.
1384
        $this->setUser($this->student);
1385
 
1386
        // Test on existing subwiki.
1387
        $result = mod_wiki_external::new_page($pagetitle, $pagecontent, 'html', $this->fpsepg1indstu->subwikiid);
1388
        $result = external_api::clean_returnvalue(mod_wiki_external::new_page_returns(), $result);
1389
        $this->assertIsInt($result['pageid']);
1390
 
1391
        $version = wiki_get_current_version($result['pageid']);
1392
        $this->assertEquals($pagecontent, $version->content);
1393
        $this->assertEquals('html', $version->contentformat);
1394
 
1395
        $page = wiki_get_page($result['pageid']);
1396
        $this->assertEquals($pagetitle, $page->title);
1397
 
1398
        // Test existing page creation.
1399
        try {
1400
            mod_wiki_external::new_page($pagetitle, $pagecontent, 'html', $this->fpsepg1indstu->subwikiid);
1401
            $this->fail('Exception expected due to creation of an existing page.');
1402
        } catch (\moodle_exception $e) {
1403
            $this->assertEquals('pageexists', $e->errorcode);
1404
        }
1405
 
1406
        // Test on non existing subwiki. Add student to group2 to have a new subwiki to be created.
1407
        $this->getDataGenerator()->create_group_member(array('userid' => $this->student->id, 'groupid' => $this->group2->id));
1408
        $result = mod_wiki_external::new_page($pagetitle, $pagecontent, 'html', null, $this->wikisepind->id, $this->student->id,
1409
            $this->group2->id);
1410
        $result = external_api::clean_returnvalue(mod_wiki_external::new_page_returns(), $result);
1411
        $this->assertIsInt($result['pageid']);
1412
 
1413
        $version = wiki_get_current_version($result['pageid']);
1414
        $this->assertEquals($pagecontent, $version->content);
1415
        $this->assertEquals('html', $version->contentformat);
1416
 
1417
        $page = wiki_get_page($result['pageid']);
1418
        $this->assertEquals($pagetitle, $page->title);
1419
 
1420
        $subwiki = wiki_get_subwiki($page->subwikiid);
1421
        $expected = new \stdClass();
1422
        $expected->id = $subwiki->id;
1423
        $expected->wikiid = $this->wikisepind->id;
1424
        $expected->groupid = $this->group2->id;
1425
        $expected->userid = $this->student->id;
1426
        $this->assertEquals($expected, $subwiki);
1427
 
1428
        // Check page creation for a user not in course.
1429
        $this->studentnotincourse = self::getDataGenerator()->create_user();
1430
        $this->anothercourse = $this->getDataGenerator()->create_course();
1431
        $this->groupnotincourse = $this->getDataGenerator()->create_group(array('courseid' => $this->anothercourse->id));
1432
 
1433
        try {
1434
            mod_wiki_external::new_page($pagetitle, $pagecontent, 'html', null, $this->wikisepind->id,
1435
                $this->studentnotincourse->id, $this->groupnotincourse->id);
1436
            $this->fail('Exception expected due to creation of an invalid subwiki creation.');
1437
        } catch (\moodle_exception $e) {
1438
            $this->assertEquals('cannoteditpage', $e->errorcode);
1439
        }
1440
 
1441
    }
1442
 
1443
    /**
1444
     * Test edit_page. We won't test all the possible cases because that's already
1445
     * done in the tests for wiki_save_section / wiki_save_page.
1446
     */
11 efrain 1447
    public function test_edit_page(): void {
1 efrain 1448
 
1449
        $this->create_individual_wikis_with_groups();
1450
 
1451
        // Test user with full capabilities.
1452
        $this->setUser($this->student);
1453
 
1454
        $newpage = $this->getDataGenerator()->get_plugin_generator('mod_wiki')->create_page($this->wikisepind,
1455
            array('group' => $this->group1->id, 'content' => 'Test'));
1456
 
1457
        // Test edit whole page.
1458
        // We add <span> in the titles to verify the WS works sending HTML in section.
1459
        $sectioncontent = '<h1><span>Title1</span></h1>Text inside section';
1460
        $newpagecontent = $sectioncontent.'<h1><span>Title2</span></h1>Text inside section';
1461
 
1462
        $result = mod_wiki_external::edit_page($newpage->id, $newpagecontent);
1463
        $result = external_api::clean_returnvalue(mod_wiki_external::edit_page_returns(), $result);
1464
        $this->assertIsInt($result['pageid']);
1465
 
1466
        $version = wiki_get_current_version($result['pageid']);
1467
        $this->assertEquals($newpagecontent, $version->content);
1468
 
1469
        // Test edit section.
1470
        $newsectioncontent = '<h1><span>Title2</span></h1>New test2';
1471
        $section = '<span>Title2</span>';
1472
 
1473
        $result = mod_wiki_external::edit_page($newpage->id, $newsectioncontent, $section);
1474
        $result = external_api::clean_returnvalue(mod_wiki_external::edit_page_returns(), $result);
1475
        $this->assertIsInt($result['pageid']);
1476
 
1477
        $expected = $sectioncontent . $newsectioncontent;
1478
 
1479
        $version = wiki_get_current_version($result['pageid']);
1480
        $this->assertEquals($expected, $version->content);
1481
 
1482
        // Test locked section.
1483
        $newsectioncontent = '<h1><span>Title2</span></h1>New test2';
1484
        $section = '<span>Title2</span>';
1485
 
1486
        try {
1487
            // Using user 1 to avoid other users to edit.
1488
            wiki_set_lock($newpage->id, 1, $section, true);
1489
            mod_wiki_external::edit_page($newpage->id, $newsectioncontent, $section);
1490
            $this->fail('Exception expected due to locked section');
1491
        } catch (\moodle_exception $e) {
1492
            $this->assertEquals('pageislocked', $e->errorcode);
1493
        }
1494
 
1495
        // Test edit non existing section.
1496
        $newsectioncontent = '<h1>Title3</h1>New test3';
1497
        $section = 'Title3';
1498
 
1499
        try {
1500
            mod_wiki_external::edit_page($newpage->id, $newsectioncontent, $section);
1501
            $this->fail('Exception expected due to non existing section in the page.');
1502
        } catch (\moodle_exception $e) {
1503
            $this->assertEquals('invalidsection', $e->errorcode);
1504
        }
1505
 
1506
    }
1507
 
1508
}