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 core_favourites;
18
 
19
use core_favourites\local\repository\favourite_repository;
20
use core_favourites\local\entity\favourite;
21
 
22
/**
23
 * Test class covering the favourite_repository.
24
 *
25
 * @package    core_favourites
26
 * @category   test
27
 * @copyright  2018 Jake Dallimore <jrhdallimore@gmail.com>
28
 * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
29
 */
1441 ariadna 30
final class repository_test extends \advanced_testcase {
1 efrain 31
 
32
    public function setUp(): void {
1441 ariadna 33
        parent::setUp();
1 efrain 34
        $this->resetAfterTest();
35
    }
36
 
37
    // Basic setup stuff to be reused in most tests.
38
    protected function setup_users_and_courses() {
39
        $user1 = self::getDataGenerator()->create_user();
40
        $user1context = \context_user::instance($user1->id);
41
        $user2 = self::getDataGenerator()->create_user();
42
        $user2context = \context_user::instance($user2->id);
43
        $course1 = self::getDataGenerator()->create_course();
44
        $course2 = self::getDataGenerator()->create_course();
45
        $course1context = \context_course::instance($course1->id);
46
        $course2context = \context_course::instance($course2->id);
47
        return [$user1context, $user2context, $course1context, $course2context];
48
    }
49
 
50
    /**
51
     * Verify the basic create operation can create records, and is validated.
52
     */
11 efrain 53
    public function test_add(): void {
1 efrain 54
        list($user1context, $user2context, $course1context, $course2context) = $this->setup_users_and_courses();
55
 
56
        // Create a favourites repository and favourite a course.
57
        $favouritesrepo = new favourite_repository($user1context);
58
 
59
        $favcourse = new favourite(
60
            'core_course',
61
            'course',
62
            $course1context->instanceid,
63
            $course1context->id,
64
            $user1context->instanceid
65
        );
66
        $timenow = time(); // Reference only, to check that the created item has a time equal to or greater than this.
67
        $favourite = $favouritesrepo->add($favcourse);
68
 
69
        // Verify we get the record back.
70
        $this->assertInstanceOf(favourite::class, $favourite);
71
        $this->assertObjectHasProperty('id', $favourite);
72
        $this->assertEquals('core_course', $favourite->component);
73
        $this->assertEquals('course', $favourite->itemtype);
74
 
75
        // Verify the returned object has additional properties, created as part of the add.
76
        $this->assertObjectHasProperty('ordering', $favourite);
77
        $this->assertObjectHasProperty('timecreated', $favourite);
78
        $this->assertGreaterThanOrEqual($timenow, $favourite->timecreated);
79
 
80
        // Try to save the same record again and confirm the store throws an exception.
81
        $this->expectException('dml_write_exception');
82
        $favouritesrepo->add($favcourse);
83
    }
84
 
85
    /**
86
     * Tests that incomplete favourites cannot be saved.
87
     */
11 efrain 88
    public function test_add_incomplete_favourite(): void {
1 efrain 89
        list($user1context, $user2context, $course1context, $course2context) = $this->setup_users_and_courses();
90
 
91
        // Create a favourites repository and try to favourite a course.
92
        $favouritesrepo = new favourite_repository($user1context);
93
 
94
        $favcourse = new favourite(
95
            'core_course',
96
            'course',
97
            $course1context->instanceid,
98
            $course1context->id,
99
            $user1context->instanceid
100
        );
101
        unset($favcourse->userid);
102
 
103
        $this->expectException('moodle_exception');
104
        $favouritesrepo->add($favcourse);
105
    }
106
 
11 efrain 107
    public function test_add_all_basic(): void {
1 efrain 108
        list($user1context, $user2context, $course1context, $course2context) = $this->setup_users_and_courses();
109
 
110
        // Create a favourites repository and favourite several courses.
111
        $favouritesrepo = new favourite_repository($user1context);
112
        $favcourses = [];
113
 
114
        $favcourses[] = new favourite(
115
            'core_course',
116
            'course',
117
            $course1context->instanceid,
118
            $course1context->id,
119
            $user1context->instanceid
120
        );
121
        $favcourses[] = new favourite(
122
            'core_course',
123
            'course',
124
            $course2context->instanceid,
125
            $course2context->id,
126
            $user1context->instanceid
127
        );
128
 
129
        $timenow = time(); // Reference only, to check that the created item has a time equal to or greater than this.
130
        $favourites = $favouritesrepo->add_all($favcourses);
131
 
132
        $this->assertIsArray($favourites);
133
        $this->assertCount(2, $favourites);
134
        foreach ($favourites as $favourite) {
135
            // Verify we get the favourite back.
136
            $this->assertInstanceOf(favourite::class, $favourite);
137
            $this->assertEquals('core_course', $favourite->component);
138
            $this->assertEquals('course', $favourite->itemtype);
139
 
140
            // Verify the returned object has additional properties, created as part of the add.
141
            $this->assertObjectHasProperty('ordering', $favourite);
142
            $this->assertObjectHasProperty('timecreated', $favourite);
143
            $this->assertGreaterThanOrEqual($timenow, $favourite->timecreated);
144
        }
145
 
146
        // Try to save the same record again and confirm the store throws an exception.
147
        $this->expectException('dml_write_exception');
148
        $favouritesrepo->add_all($favcourses);
149
    }
150
 
151
    /**
152
     * Tests reading from the repository by instance id.
153
     */
11 efrain 154
    public function test_find(): void {
1 efrain 155
        list($user1context, $user2context, $course1context, $course2context) = $this->setup_users_and_courses();
156
 
157
        // Create a favourites repository and favourite a course.
158
        $favouritesrepo = new favourite_repository($user1context);
159
        $favourite = new favourite(
160
            'core_course',
161
            'course',
162
            $course1context->instanceid,
163
            $course1context->id,
164
            $user1context->instanceid
165
        );
166
        $favourite = $favouritesrepo->add($favourite);
167
 
168
        // Now, from the repo, get the single favourite we just created, by id.
169
        $userfavourite = $favouritesrepo->find($favourite->id);
170
        $this->assertInstanceOf(favourite::class, $userfavourite);
171
        $this->assertObjectHasProperty('timecreated', $userfavourite);
172
 
173
        // Try to get a favourite we know doesn't exist.
174
        // We expect an exception in this case.
175
        $this->expectException(\dml_exception::class);
176
        $favouritesrepo->find(0);
177
    }
178
 
179
    /**
180
     * Test verifying that find_all() returns all favourites, or an empty array.
181
     */
11 efrain 182
    public function test_find_all(): void {
1 efrain 183
        list($user1context, $user2context, $course1context, $course2context) = $this->setup_users_and_courses();
184
 
185
        $favouritesrepo = new favourite_repository($user1context);
186
 
187
        // Verify that only two self-conversations are found.
188
        $this->assertCount(2, $favouritesrepo->find_all());
189
 
190
        // Save a favourite for 2 courses, in different areas.
191
        $favourite = new favourite(
192
            'core_course',
193
            'course',
194
            $course1context->instanceid,
195
            $course1context->id,
196
            $user1context->instanceid
197
        );
198
        $favourite2 = new favourite(
199
            'core_course',
200
            'course',
201
            $course2context->instanceid,
202
            $course2context->id,
203
            $user1context->instanceid
204
        );
205
        $favouritesrepo->add($favourite);
206
        $favouritesrepo->add($favourite2);
207
 
208
        // Verify that find_all returns both of our favourites + two self-conversations.
209
        $favourites = $favouritesrepo->find_all();
210
        $this->assertCount(4, $favourites);
211
        foreach ($favourites as $fav) {
212
            $this->assertInstanceOf(favourite::class, $fav);
213
            $this->assertObjectHasProperty('id', $fav);
214
            $this->assertObjectHasProperty('timecreated', $fav);
215
        }
216
    }
217
 
218
    /**
219
     * Testing the pagination of the find_all method.
220
     */
11 efrain 221
    public function test_find_all_pagination(): void {
1 efrain 222
        list($user1context, $user2context, $course1context, $course2context) = $this->setup_users_and_courses();
223
 
224
        $favouritesrepo = new favourite_repository($user1context);
225
 
226
        // Verify that for an empty repository, find_all with any combination of page options returns only self-conversations.
227
        $this->assertCount(2, $favouritesrepo->find_all(0, 0));
228
        $this->assertCount(2, $favouritesrepo->find_all(0, 10));
229
        $this->assertCount(1, $favouritesrepo->find_all(1, 0));
230
        $this->assertCount(1, $favouritesrepo->find_all(1, 10));
231
 
232
        // Save 10 arbitrary favourites to the repo.
233
        foreach (range(1, 10) as $i) {
234
            $favourite = new favourite(
235
                'core_course',
236
                'course',
237
                $i,
238
                $course1context->id,
239
                $user1context->instanceid
240
            );
241
            $favouritesrepo->add($favourite);
242
        }
243
 
244
        // Verify we have 10 favourites + 2 self-conversations.
245
        $this->assertEquals(12, $favouritesrepo->count());
246
 
247
        // Verify we can fetch the first page of 5 records+ 2 self-conversations.
248
        $favourites = $favouritesrepo->find_all(0, 6);
249
        $this->assertCount(6, $favourites);
250
 
251
        // Verify we can fetch the second page.
252
        $favourites = $favouritesrepo->find_all(6, 6);
253
        $this->assertCount(6, $favourites);
254
 
255
        // Verify the third page request ends with an empty array.
256
        $favourites = $favouritesrepo->find_all(12, 6);
257
        $this->assertCount(0, $favourites);
258
    }
259
 
260
    /**
261
     * Test retrieval of a user's favourites for a given criteria, in this case, area.
262
     */
11 efrain 263
    public function test_find_by(): void {
1 efrain 264
        list($user1context, $user2context, $course1context, $course2context) = $this->setup_users_and_courses();
265
 
266
        // Create a favourites repository and favourite a course.
267
        $favouritesrepo = new favourite_repository($user1context);
268
        $favourite = new favourite(
269
            'core_course',
270
            'course',
271
            $course1context->instanceid,
272
            $course1context->id,
273
            $user1context->instanceid
274
        );
275
        $favouritesrepo->add($favourite);
276
 
277
        // Add another favourite.
278
        $favourite = new favourite(
279
            'core_course',
280
            'course_item',
281
            $course1context->instanceid,
282
            $course1context->id,
283
            $user1context->instanceid
284
        );
285
        $favouritesrepo->add($favourite);
286
 
287
        // From the repo, get the list of favourites for the 'core_course/course' area.
288
        $userfavourites = $favouritesrepo->find_by(['component' => 'core_course', 'itemtype' => 'course']);
289
        $this->assertIsArray($userfavourites);
290
        $this->assertCount(1, $userfavourites);
291
 
292
        // Try to get a list of favourites for a non-existent area.
293
        $userfavourites = $favouritesrepo->find_by(['component' => 'core_cannibalism', 'itemtype' => 'course']);
294
        $this->assertIsArray($userfavourites);
295
        $this->assertCount(0, $userfavourites);
296
 
297
        // From the repo, get the list of favourites for the 'core_course/course' area when passed as an array.
298
        $userfavourites = $favouritesrepo->find_by(['component' => 'core_course', 'itemtype' => ['course']]);
299
        $this->assertIsArray($userfavourites);
300
        $this->assertCount(1, $userfavourites);
301
 
302
        // From the repo, get the list of favourites for the 'core_course' area given multiple item_types.
303
        $userfavourites = $favouritesrepo->find_by(['component' => 'core_course', 'itemtype' => ['course', 'course_item']]);
304
        $this->assertIsArray($userfavourites);
305
        $this->assertCount(2, $userfavourites);
306
    }
307
 
308
    /**
309
     * Testing the pagination of the find_by method.
310
     */
11 efrain 311
    public function test_find_by_pagination(): void {
1 efrain 312
        list($user1context, $user2context, $course1context, $course2context) = $this->setup_users_and_courses();
313
 
314
        $favouritesrepo = new favourite_repository($user1context);
315
 
316
        // Verify that by default, find_all with any combination of page options returns only self-conversations.
317
        $this->assertCount(2, $favouritesrepo->find_by([], 0, 0));
318
        $this->assertCount(2, $favouritesrepo->find_by([], 0, 10));
319
        $this->assertCount(1, $favouritesrepo->find_by([], 1, 0));
320
        $this->assertCount(1, $favouritesrepo->find_by([], 1, 10));
321
 
322
        // Save 10 arbitrary favourites to the repo.
323
        foreach (range(1, 10) as $i) {
324
            $favourite = new favourite(
325
                'core_course',
326
                'course',
327
                $i,
328
                $course1context->id,
329
                $user1context->instanceid
330
            );
331
            $favouritesrepo->add($favourite);
332
        }
333
 
334
        // Verify we have 10 favourites + 2 self-conversations.
335
        $this->assertEquals(12, $favouritesrepo->count());
336
 
337
        // Verify a request for a page, when no criteria match, results in 2 self-conversations array.
338
        $favourites = $favouritesrepo->find_by(['component' => 'core_message'], 0, 5);
339
        $this->assertCount(2, $favourites);
340
 
341
        // Verify we can fetch a the first page of 5 records.
342
        $favourites = $favouritesrepo->find_by(['component' => 'core_course'], 0, 5);
343
        $this->assertCount(5, $favourites);
344
 
345
        // Verify we can fetch the second page.
346
        $favourites = $favouritesrepo->find_by(['component' => 'core_course'], 5, 5);
347
        $this->assertCount(5, $favourites);
348
 
349
        // Verify the third page request ends with an empty array.
350
        $favourites = $favouritesrepo->find_by(['component' => 'core_course'], 10, 5);
351
        $this->assertCount(0, $favourites);
352
    }
353
 
354
    /**
355
     * Test the count_by() method.
356
     */
11 efrain 357
    public function test_count_by(): void {
1 efrain 358
        list($user1context, $user2context, $course1context, $course2context) = $this->setup_users_and_courses();
359
 
360
        // Create a favourites repository and add 2 favourites in different areas.
361
        $favouritesrepo = new favourite_repository($user1context);
362
        $favourite = new favourite(
363
            'core_course',
364
            'course',
365
            $course1context->instanceid,
366
            $course1context->id,
367
            $user1context->instanceid
368
        );
369
        $favourite2 = new favourite(
370
            'core_course',
371
            'anothertype',
372
            $course2context->instanceid,
373
            $course2context->id,
374
            $user1context->instanceid
375
        );
376
        $favouritesrepo->add($favourite);
377
        $favouritesrepo->add($favourite2);
378
 
379
        // Verify counts can be restricted by criteria.
380
        $this->assertEquals(1, $favouritesrepo->count_by(['userid' => $user1context->instanceid, 'component' => 'core_course',
381
                'itemtype' => 'course']));
382
        $this->assertEquals(1, $favouritesrepo->count_by(['userid' => $user1context->instanceid, 'component' => 'core_course',
383
            'itemtype' => 'anothertype']));
384
        $this->assertEquals(0, $favouritesrepo->count_by(['userid' => $user1context->instanceid, 'component' => 'core_course',
385
            'itemtype' => 'nonexistenttype']));
386
    }
387
 
388
    /**
389
     * Test the exists() function.
390
     */
11 efrain 391
    public function test_exists(): void {
1 efrain 392
        list($user1context, $user2context, $course1context, $course2context) = $this->setup_users_and_courses();
393
 
394
        // Create a favourites repository and favourite a course.
395
        $favouritesrepo = new favourite_repository($user1context);
396
        $favourite = new favourite(
397
            'core_course',
398
            'course',
399
            $course1context->instanceid,
400
            $course1context->id,
401
            $user1context->instanceid
402
        );
403
        $createdfavourite = $favouritesrepo->add($favourite);
404
 
405
        // Verify the existence of the favourite in the repo.
406
        $this->assertTrue($favouritesrepo->exists($createdfavourite->id));
407
 
408
        // Verify exists returns false for non-existent favourite.
409
        $this->assertFalse($favouritesrepo->exists(0));
410
    }
411
 
412
    /**
413
     * Test the exists_by() method.
414
     */
11 efrain 415
    public function test_exists_by(): void {
1 efrain 416
        list($user1context, $user2context, $course1context, $course2context) = $this->setup_users_and_courses();
417
 
418
        // Create a favourites repository and favourite two courses, in different areas.
419
        $favouritesrepo = new favourite_repository($user1context);
420
        $favourite = new favourite(
421
            'core_course',
422
            'course',
423
            $course1context->instanceid,
424
            $course1context->id,
425
            $user1context->instanceid
426
        );
427
        $favourite2 = new favourite(
428
            'core_course',
429
            'anothertype',
430
            $course2context->instanceid,
431
            $course2context->id,
432
            $user1context->instanceid
433
        );
434
        $favourite1 = $favouritesrepo->add($favourite);
435
        $favourite2 = $favouritesrepo->add($favourite2);
436
 
437
        // Verify the existence of the favourites.
438
        $this->assertTrue($favouritesrepo->exists_by(
439
            [
440
                'userid' => $user1context->instanceid,
441
                'component' => 'core_course',
442
                'itemtype' => 'course',
443
                'itemid' => $favourite1->itemid,
444
                'contextid' => $favourite1->contextid
445
            ]
446
        ));
447
        $this->assertTrue($favouritesrepo->exists_by(
448
            [
449
                'userid' => $user1context->instanceid,
450
                'component' => 'core_course',
451
                'itemtype' => 'anothertype',
452
                'itemid' => $favourite2->itemid,
453
                'contextid' => $favourite2->contextid
454
            ]
455
        ));
456
 
457
        // Verify that we can't find a favourite from one area, in another.
458
        $this->assertFalse($favouritesrepo->exists_by(
459
            [
460
                'userid' => $user1context->instanceid,
461
                'component' => 'core_course',
462
                'itemtype' => 'anothertype',
463
                'itemid' => $favourite1->itemid,
464
                'contextid' => $favourite1->contextid
465
            ]
466
        ));
467
    }
468
 
469
    /**
470
     * Test the update() method, by simulating a user changing the ordering of a favourite.
471
     */
11 efrain 472
    public function test_update(): void {
1 efrain 473
        list($user1context, $user2context, $course1context, $course2context) = $this->setup_users_and_courses();
474
 
475
        // Create a favourites repository and favourite a course.
476
        $favouritesrepo = new favourite_repository($user1context);
477
        $favourite = new favourite(
478
            'core_course',
479
            'course',
480
            $course1context->instanceid,
481
            $course1context->id,
482
            $user1context->instanceid
483
        );
484
        $favourite1 = $favouritesrepo->add($favourite);
485
        $this->assertNull($favourite1->ordering);
486
 
487
        // Verify we can update the ordering for 2 favourites.
488
        $favourite1->ordering = 1;
489
        $favourite1 = $favouritesrepo->update($favourite1);
490
        $this->assertInstanceOf(favourite::class, $favourite1);
491
        $this->assertEquals('1', $favourite1->ordering);
492
    }
493
 
11 efrain 494
    public function test_delete(): void {
1 efrain 495
        list($user1context, $user2context, $course1context, $course2context) = $this->setup_users_and_courses();
496
 
497
        // Create a favourites repository and favourite a course.
498
        $favouritesrepo = new favourite_repository($user1context);
499
        $favourite = new favourite(
500
            'core_course',
501
            'course',
502
            $course1context->instanceid,
503
            $course1context->id,
504
            $user1context->instanceid
505
        );
506
        $favourite = $favouritesrepo->add($favourite);
507
 
508
        // Verify the existence of the favourite in the repo.
509
        $this->assertTrue($favouritesrepo->exists($favourite->id));
510
 
511
        // Now, delete the favourite and confirm it's not retrievable.
512
        $favouritesrepo->delete($favourite->id);
513
        $this->assertFalse($favouritesrepo->exists($favourite->id));
514
    }
515
 
516
    /**
517
     * Test the delete_by() method.
518
     */
11 efrain 519
    public function test_delete_by(): void {
1 efrain 520
        list($user1context, $user2context, $course1context, $course2context) = $this->setup_users_and_courses();
521
 
522
        // Create a favourites repository and favourite two courses, in different areas.
523
        $favouritesrepo = new favourite_repository($user1context);
524
        $favourite = new favourite(
525
            'core_course',
526
            'course',
527
            $course1context->instanceid,
528
            $course1context->id,
529
            $user1context->instanceid
530
        );
531
        $favourite2 = new favourite(
532
            'core_course',
533
            'anothertype',
534
            $course1context->instanceid,
535
            $course1context->id,
536
            $user1context->instanceid
537
        );
538
        $favourite1 = $favouritesrepo->add($favourite);
539
        $favourite2 = $favouritesrepo->add($favourite2);
540
 
541
        // Verify we have 2 items in the repo + 2 self-conversations.
542
        $this->assertEquals(4, $favouritesrepo->count());
543
 
544
        // Try to delete by a non-existent area, and confirm it doesn't remove anything.
545
        $favouritesrepo->delete_by(
546
            [
547
                'userid' => $user1context->instanceid,
548
                'component' => 'core_course',
549
                'itemtype' => 'donaldduck'
550
            ]
551
        );
552
        $this->assertEquals(4, $favouritesrepo->count());
553
 
554
        // Try to delete by a non-existent area, and confirm it doesn't remove anything.
555
        $favouritesrepo->delete_by(
556
            [
557
                'userid' => $user1context->instanceid,
558
                'component' => 'core_course',
559
                'itemtype' => 'cat'
560
            ]
561
        );
562
        $this->assertEquals(4, $favouritesrepo->count());
563
 
564
        // Delete by area, and confirm we have one record left, from the 'core_course/anothertype' area.
565
        $favouritesrepo->delete_by(
566
            [
567
                'userid' => $user1context->instanceid,
568
                'component' => 'core_course',
569
                'itemtype' => 'course'
570
            ]
571
        );
572
        $this->assertEquals(3, $favouritesrepo->count());
573
        $this->assertFalse($favouritesrepo->exists($favourite1->id));
574
        $this->assertTrue($favouritesrepo->exists($favourite2->id));
575
    }
576
 
577
    /**
578
     * Test the find_favourite() method for an existing favourite.
579
     */
11 efrain 580
    public function test_find_favourite_basic(): void {
1 efrain 581
        list($user1context, $user2context, $course1context, $course2context) = $this->setup_users_and_courses();
582
 
583
        // Create a favourites repository and favourite two courses, in different areas.
584
        $favouritesrepo = new favourite_repository($user1context);
585
        $favourite = new favourite(
586
            'core_course',
587
            'course',
588
            $course1context->instanceid,
589
            $course1context->id,
590
            $user1context->instanceid
591
        );
592
        $favourite2 = new favourite(
593
            'core_course',
594
            'anothertype',
595
            $course1context->instanceid,
596
            $course1context->id,
597
            $user1context->instanceid
598
        );
599
        $favourite1 = $favouritesrepo->add($favourite);
600
        $favourite2 = $favouritesrepo->add($favourite2);
601
 
602
        $fav = $favouritesrepo->find_favourite($user1context->instanceid, 'core_course', 'course', $course1context->instanceid,
603
            $course1context->id);
604
        $this->assertInstanceOf(\core_favourites\local\entity\favourite::class, $fav);
605
    }
606
 
607
    /**
608
     * Test confirming the repository throws an exception in find_favourite if the favourite can't be found.
609
     */
11 efrain 610
    public function test_find_favourite_nonexistent_favourite(): void {
1 efrain 611
        list($user1context, $user2context, $course1context, $course2context) = $this->setup_users_and_courses();
612
 
613
        // Confirm we get an exception.
614
        $favouritesrepo = new favourite_repository($user1context);
615
        $this->expectException(\dml_exception::class);
616
        $favouritesrepo->find_favourite($user1context->instanceid, 'core_course', 'course', 0, $course1context->id);
617
    }
618
}