Proyectos de Subversion Moodle

Rev

Rev 1 | | 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
namespace mod_bigbluebuttonbn\local;
17
 
18
use backup;
19
use backup_controller;
20
use mod_bigbluebuttonbn\completion\custom_completion;
21
use mod_bigbluebuttonbn\extension;
22
use mod_bigbluebuttonbn\instance;
23
use mod_bigbluebuttonbn\local\extension\mod_instance_helper;
24
use mod_bigbluebuttonbn\meeting;
25
use mod_bigbluebuttonbn\test\subplugins_test_helper_trait;
26
use mod_bigbluebuttonbn\test\testcase_helper_trait;
27
use restore_controller;
28
use restore_dbops;
29
 
30
/**
31
 * Extension helper class test
32
 *
33
 * @package   mod_bigbluebuttonbn
34
 * @copyright 2023 - present, Blindside Networks Inc
35
 * @license   http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
36
 * @author    Laurent David (laurent@call-learning.fr)
37
 * @coversDefaultClass \mod_bigbluebuttonbn\extension
38
 */
39
class extension_test extends \advanced_testcase {
40
    use subplugins_test_helper_trait;
41
    use testcase_helper_trait;
42
 
43
    /**
44
     * Setup our fake plugin
45
     *
46
     * @return void
47
     */
48
    public function setUp(): void {
49
        $this->resetAfterTest(true);
50
        $this->setup_fake_plugin('simple');
51
        $this->resetDebugging(); // We might have debugging messages issued from setup_fake_plugin here that we need to get rid of.
52
    }
53
 
54
 
55
    /**
56
     * Setup our fake plugin
57
     *
58
     * @return void
59
     */
60
    public function tearDown(): void {
61
        $this->uninstall_fake_plugin('simple');
62
    }
63
 
64
    /**
65
     * Test for the type_text provider.
66
     *
67
     * @param bool $bbbenabled
68
     * @param string $apiclass
69
     * @param array $extensionclasses
70
     *
71
     * @dataProvider classes_implementing_class
72
     * @covers       \mod_bigbluebuttonbn\extension::get_instances_implementing
73
     */
74
    public function test_get_class_implementing(bool $bbbenabled, string $apiclass, array $extensionclasses): void {
75
        $this->enable_plugins($bbbenabled);
76
        // Make the method public so we can test it.
77
        $reflectionextension = new \ReflectionClass(extension::class);
78
        $getclassimplementing = $reflectionextension->getMethod('get_instances_implementing');
79
        $allfoundinstances = $getclassimplementing->invoke(null, $apiclass);
80
        $foundclasses = array_map(
81
            function($instance) {
82
                return get_class($instance);
83
            },
84
            $allfoundinstances
85
        );
86
        $this->assertEquals($extensionclasses, $foundclasses);
87
    }
88
 
89
    /**
90
     * Test the add module callback
91
     *
92
     * @return void
93
     * @covers \mod_bigbluebuttonbn\local\extension\mod_instance_helper
94
     */
11 efrain 95
    public function test_mod_instance_helper_add(): void {
1 efrain 96
        global $DB;
97
        // Enable plugin.
98
        $this->enable_plugins(true);
99
 
100
        $course = $this->getDataGenerator()->create_course();
101
        $record = $this->getDataGenerator()->create_module(
102
            'bigbluebuttonbn',
103
            ['course' => $course->id, 'newfield' => 2]
104
        );
105
        $this->assertEquals(2, $DB->get_field('bbbext_simple', 'newfield', ['bigbluebuttonbnid' => $record->id]));
106
    }
107
 
108
    /**
109
     * Test the update module callback
110
     *
111
     * @return void
112
     * @covers \mod_bigbluebuttonbn\local\extension\mod_instance_helper
113
     */
11 efrain 114
    public function test_mod_instance_helper_update(): void {
1 efrain 115
        global $DB;
116
        $this->setAdminUser();
117
        // Enable plugin.
118
        $this->enable_plugins(true);
119
 
120
        $course = $this->getDataGenerator()->create_course();
121
        $record = $this->getDataGenerator()->create_module('bigbluebuttonbn', ['course' => $course->id, 'newfield' => 2]);
122
        $cm = get_fast_modinfo($course)->instances['bigbluebuttonbn'][$record->id];
123
        [$cm, $context, $moduleinfo, $data] = get_moduleinfo_data($cm, $course);
124
        $data->newfield = 3;
125
        bigbluebuttonbn_update_instance($data);
126
        $this->assertEquals(3, $DB->get_field('bbbext_simple', 'newfield', ['bigbluebuttonbnid' => $record->id]));
127
    }
128
 
129
    /**
130
     * Test delete module callback
131
     *
132
     * @return void
133
     * @covers \mod_bigbluebuttonbn\local\extension\mod_instance_helper
134
     */
11 efrain 135
    public function test_mod_instance_helper_delete(): void {
1 efrain 136
        global $DB;
137
        $this->initialise_mock_server();
138
        // Enable plugin.
139
        $this->enable_plugins(true);
140
 
141
        $course = $this->getDataGenerator()->create_course();
142
        $record = $this->getDataGenerator()->create_module('bigbluebuttonbn', ['course' => $course->id, 'newfield' => 2]);
143
        $cm = get_fast_modinfo($course)->instances['bigbluebuttonbn'][$record->id];
144
        course_delete_module($cm->id, false);
145
        $this->assertFalse($DB->get_field('bbbext_simple', 'newfield', ['bigbluebuttonbnid' => $record->id]));
146
    }
147
 
148
    /**
149
     * Test the action_url_addons with plugin enabled
150
     *
151
     * @return void
152
     * @covers \mod_bigbluebuttonbn\extension::action_url_addons
153
     */
11 efrain 154
    public function test_action_url_addons(): void {
1 efrain 155
        // Enable plugin.
156
        $this->enable_plugins(true);
157
        $course = $this->get_course();
158
        [$cm, $cminfo, $bbactivity] = $this->create_instance($course);
159
        $bbactivity->newfield = 4;
160
        extension::update_instance($bbactivity);
161
        ['data' => $additionalvar1, 'metadata' => $additionalvar2] =
162
            extension::action_url_addons('create', [], ['bbb-meta' => 'Test'], $bbactivity->id);
163
        $this->assertEmpty($additionalvar1);
164
        $this->assertCount(2, $additionalvar2);
165
        $this->assertEquals($additionalvar2['newfield'], 4);
166
        ['data' => $additionalvar1, 'metadata' => $additionalvar2] = extension::action_url_addons('delete');
167
        $this->assertEmpty($additionalvar1);
168
        $this->assertEmpty($additionalvar2);
169
    }
170
 
171
    /**
172
     * Test the action_url_addons with plugin enabled
173
     *
174
     * @return void
175
     * @covers \mod_bigbluebuttonbn\extension::action_url_addons
176
     */
11 efrain 177
    public function test_join_url_with_additional_field(): void {
1 efrain 178
        $this->initialise_mock_server();
179
        // Enable plugin.
180
        $this->enable_plugins(true);
181
        $course = $this->get_course();
182
        [$cm, $cminfo, $bbactivity] = $this->create_instance($course);
183
        $bbactivity->newfield = 4;
184
        extension::update_instance($bbactivity);
185
        $instance = instance::get_from_instanceid($bbactivity->id);
186
        $meeting = new meeting($instance);
187
        $meetingjoinurl = $meeting->get_join_url();
188
        $this->assertStringContainsString('newfield=4', $meetingjoinurl);
189
    }
190
 
191
    /**
192
     * Test backup restore (with extension)
193
     *
194
     * @covers       \backup_bigbluebuttonbn_activity_task
195
     */
196
    public function test_backup_restore(): void {
197
        global $DB, $CFG, $USER;
198
        require_once($CFG->dirroot . '/backup/util/includes/restore_includes.php');
199
        require_once($CFG->dirroot . '/backup/util/includes/backup_includes.php');
200
        $this->resetAfterTest();
201
        $course = $this->get_course();
202
        [$cm, $cminfo, $bbactivity] = $this->create_instance($course);
203
        $bbactivity->newfield = 4;
204
        extension::update_instance($bbactivity);
205
 
206
        $this->setAdminUser();
207
 
208
        $CFG->backup_file_logger_level = backup::LOG_NONE;
209
 
210
        // Do backup with default settings.
211
        set_config('backup_general_users', 1, 'backup');
212
        $bc = new backup_controller(backup::TYPE_1COURSE, $course->id,
213
            backup::FORMAT_MOODLE, backup::INTERACTIVE_NO, backup::MODE_GENERAL,
214
            $USER->id);
215
        $bc->execute_plan();
216
        $results = $bc->get_results();
217
        $file = $results['backup_destination'];
218
        $fp = get_file_packer('application/vnd.moodle.backup');
219
        $filepath = $CFG->dataroot . '/temp/backup/test-restore-course';
220
        $file->extract_to_pathname($fp, $filepath);
221
        $bc->destroy();
222
 
223
        // Do restore to new course with default settings.
224
        $newcourseid = restore_dbops::create_new_course(
225
            $course->fullname, $course->shortname . '_2', $course->category);
226
        $rc = new restore_controller('test-restore-course', $newcourseid,
227
            backup::INTERACTIVE_NO, backup::MODE_GENERAL, $USER->id,
228
            backup::TARGET_NEW_COURSE);
229
        $rc->execute_precheck();
230
        $rc->execute_plan();
231
        $rc->destroy();
232
        $cms = get_fast_modinfo($newcourseid)->get_cms();
233
        $newmoduleid = null;
234
        foreach ($cms as $id => $cm) {
235
            if ($cm->modname == 'bigbluebuttonbn') {
236
                $newmoduleid = $cm->instance;
237
            }
238
        }
239
        // Check instance has been copied.
240
        $this->assertNotNull($newmoduleid);
241
 
242
        // Change the original instance value (this makes sure we are not looking at the same value in the
243
        // original and copy).
244
        $bbactivity->newfield = 5;
245
        extension::update_instance($bbactivity);
246
 
247
        // Now check the copied instance.
248
        $newfieldrecord = $DB->get_record('bbbext_simple', [
249
            'bigbluebuttonbnid' => $newmoduleid,
250
        ]);
251
        $this->assertNotNull($newfieldrecord);
252
        $this->assertEquals(4, $newfieldrecord->newfield);
253
        // And the original.
254
        $oldfieldrecord = $DB->get_record('bbbext_simple', [
255
            'bigbluebuttonbnid' => $bbactivity->id,
256
        ]);
257
        $this->assertNotNull($oldfieldrecord);
258
        $this->assertEquals(5, $oldfieldrecord->newfield);
259
    }
260
 
261
    /**
262
     * Test completion with and without addons.
263
     *
264
     * @param array $customcompletionrules
265
     * @param array $events
266
     * @param int $expectedstate
267
     * @return void
268
     * @dataProvider custom_completion_data_provider
269
     * @covers \mod_bigbluebuttonbn\local\extension\custom_completion_addons
270
     */
271
    public function test_additional_completion(array $customcompletionrules, array $events, int $expectedstate): void {
272
        // Enable plugin.
273
        $this->enable_plugins(true);
274
        $this->initialise_mock_server();
275
        list($bbactivitycontext, $bbactivitycm, $bbactivity) = $this->create_instance(
276
            $this->get_course(),
277
            array_merge([
278
                'completion' => '2',
279
            ], $customcompletionrules)
280
        );
281
 
282
        $plugingenerator = $this->getDataGenerator()->get_plugin_generator('mod_bigbluebuttonbn');
283
 
284
        $user = $this->getDataGenerator()->create_user();
285
        $this->setUser($user);
286
 
287
        // Now create a couple of events.
288
        $instance = instance::get_from_instanceid($bbactivity->id);
289
        set_config('bigbluebuttonbn_meetingevents_enabled', true);
290
        $meeting = $plugingenerator->create_meeting([
291
            'instanceid' => $instance->get_instance_id(),
292
            'groupid' => $instance->get_group_id(),
293
            'participants' => json_encode([$user->id]),
294
        ]);
295
        foreach ($events as $edesc) {
296
            $plugingenerator->add_meeting_event($user, $instance, $edesc->name, $edesc->data ?? '');
297
        }
298
        $result = $plugingenerator->send_all_events($instance);
299
        $this->assertNotEmpty($result->data);
300
        $data = json_decode(json_encode($result->data));
301
        meeting::meeting_events($instance, $data);
302
        $completion = new custom_completion($bbactivitycm, $user->id);
303
        $result = $completion->get_overall_completion_state();
304
        $this->assertEquals($expectedstate, $result);
305
 
306
    }
307
 
308
    /**
309
     * Data generator
310
     *
311
     * @return array[]
312
     */
313
    public static function custom_completion_data_provider(): array {
314
        global $CFG;
315
        require_once($CFG->libdir . '/completionlib.php');
316
        return [
317
            'simple' => [
318
                'customcompletionrules' => [
319
                    'completionengagementtalks' => 1,
320
                    'completionextraisehandtwice' => 1,
321
                ],
322
                'events' => [
323
                    (object) ['name' => 'talks'],
324
                    (object) ['name' => 'raisehand'],
325
                    (object) ['name' => 'raisehand'],
326
                ],
327
                'expectedstate' => COMPLETION_COMPLETE,
328
            ],
329
            'not right events' => [
330
                'customcompletionrules' => [
331
                    'completionextraisehandtwice' => 1,
332
                ],
333
                'events' => [
334
                    (object) ['name' => 'chats'],
335
                ],
336
                'expectedstate' => COMPLETION_INCOMPLETE,
337
            ],
338
            'not enough events' => [
339
                'customcompletionrules' => [
340
                    'completionextraisehandtwice' => 1,
341
                ],
342
                'events' => [
343
                    (object) ['name' => 'raisehand'],
344
                ],
345
                'expectedstate' => COMPLETION_INCOMPLETE,
346
            ],
347
            'more events' => [
348
                'customcompletionrules' => [
349
                    'completionengagementtalks' => 1,
350
                ],
351
                'events' => [
352
                    (object) ['name' => 'talks'],
353
                    (object) ['name' => 'talks'],
354
                    (object) ['name' => 'talks'],
355
                ],
356
                'expectedstate' => COMPLETION_COMPLETE,
357
            ],
358
            'basics are still working' => [
359
                'customcompletionrules' => [
360
                    'completionengagementtalks' => 1,
361
                ],
362
                'events' => [
363
                    (object) ['name' => 'talks'],
364
                ],
365
                'expectedstate' => COMPLETION_COMPLETE,
366
            ],
367
        ];
368
    }
369
 
370
    /**
371
     * Data provider for testing get_class_implementing
372
     *
373
     * @return array[]
374
     */
375
    public function classes_implementing_class(): array {
376
        return [
377
            'mod_instance_helper with plugin disabled' => [
378
                'bbbenabled' => false,
379
                'apiclass' => mod_instance_helper::class,
380
                'result' => [],
381
            ],
382
            'mod_instance_helper with plugin enabled' => [
383
                'bbbenabled' => true,
384
                'apiclass' => mod_instance_helper::class,
385
                'result' => [
386
                    'bbbext_simple\\bigbluebuttonbn\\mod_instance_helper',
387
                ],
388
            ],
389
        ];
390
    }
391
 
392
    /**
393
     * Enable plugins
394
     *
395
     * @param bool $bbbenabled
396
     * @return void
397
     */
398
    private function enable_plugins(bool $bbbenabled) {
399
        // First make sure that either BBB is enabled or not.
400
        \core\plugininfo\mod::enable_plugin('bigbluebuttonbn', $bbbenabled ? 1 : 0);
401
        $plugin = extension::BBB_EXTENSION_PLUGIN_NAME . '_simple';
402
        if ($bbbenabled) {
403
            unset_config('disabled', $plugin);
404
        } else {
405
            set_config('disabled', 'disabled', $plugin);
406
        }
407
    }
408
}