Passed
Push — master ( 7b6b24...78c3b4 )
by Julito
24:27 queued 15:59
created

GroupManager::update_category()   A

Complexity

Conditions 4
Paths 6

Size

Total Lines 66
Code Lines 43

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 4
eloc 43
nc 6
nop 15
dl 0
loc 66
rs 9.232
c 0
b 0
f 0

How to fix   Long Method    Many Parameters   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

Many Parameters

Methods with many parameters are not only hard to understand, but their parameters also often become inconsistent when you need more, or different data.

There are several approaches to avoid long parameter lists:

1
<?php
2
3
/* For licensing terms, see /license.txt */
4
5
use Chamilo\CoreBundle\Entity\Course;
6
use Chamilo\CoreBundle\Entity\User;
7
use Chamilo\CoreBundle\Framework\Container;
8
use Chamilo\CourseBundle\Entity\CGroup;
9
use Chamilo\CourseBundle\Entity\CGroupCategory;
10
use Doctrine\Common\Collections\ArrayCollection;
11
use Doctrine\Common\Collections\Criteria;
12
13
/**
14
 * This library contains some functions for group-management.
15
 *
16
 * @author Bart Mollet
17
 *
18
 * @todo Add $course_code parameter to all functions. So this GroupManager can
19
 * be used outside a session.
20
 */
21
class GroupManager
22
{
23
    /* DEFAULT_GROUP_CATEGORY:
24
    When group categories aren't available (platform-setting),
25
    all groups are created in this 'dummy'-category*/
26
    public const DEFAULT_GROUP_CATEGORY = 2;
27
28
    /**
29
     * infinite.
30
     */
31
    public const INFINITE = 99999;
32
    /**
33
     * No limit on the number of users in a group.
34
     */
35
    public const MEMBER_PER_GROUP_NO_LIMIT = 0;
36
    /**
37
     * No limit on the number of groups per user.
38
     */
39
    public const GROUP_PER_MEMBER_NO_LIMIT = 0;
40
    /**
41
     * The tools of a group can have 3 states
42
     * - not available
43
     * - public
44
     * - private.
45
     */
46
    public const TOOL_NOT_AVAILABLE = 0;
47
    public const TOOL_PUBLIC = 1;
48
    public const TOOL_PRIVATE = 2;
49
    public const TOOL_PRIVATE_BETWEEN_USERS = 3;
50
51
    /**
52
     * Constants for the available group tools.
53
     */
54
    public const GROUP_TOOL_FORUM = 0;
55
    public const GROUP_TOOL_DOCUMENTS = 1;
56
    public const GROUP_TOOL_CALENDAR = 2;
57
    public const GROUP_TOOL_ANNOUNCEMENT = 3;
58
    public const GROUP_TOOL_WORK = 4;
59
    public const GROUP_TOOL_WIKI = 5;
60
    public const GROUP_TOOL_CHAT = 6;
61
62
    public const DOCUMENT_MODE_SHARE = 0; // By default
63
    public const DOCUMENT_MODE_READ_ONLY = 1;
64
    public const DOCUMENT_MODE_COLLABORATION = 2;
65
66
    public function __construct()
67
    {
68
    }
69
70
    /**
71
     * @param int $courseId
72
     *
73
     * @return CGroup[]
74
     */
75
    public static function get_groups($courseId = 0)
76
    {
77
        $repo = Container::getGroupRepository();
78
        $course = api_get_course_entity($courseId);
79
        if (null !== $course) {
80
            return [];
81
        }
82
83
        $qb = $repo->getResourcesByCourse($course);
84
85
        return $qb->getQuery()->getResult();
86
        /*$table_group = Database::get_course_table(TABLE_GROUP);
87
        $courseId = !empty($courseId) ? (int) $courseId : api_get_course_int_id();
88
89
        $sql = "SELECT * FROM $table_group WHERE c_id = $courseId  ";
90
        $result = Database::query($sql);
91
92
        return Database::store_result($result, 'ASSOC');*/
93
    }
94
95
    /**
96
     * Get list of groups for current course.
97
     *
98
     * @param int    $categoryId The id of the category from which the groups are
99
     *                           requested
100
     * @param Course $course     Default is current course
101
     * @param int    $status     group status
102
     * @param int    $sessionId
103
     * @param bool   $getCount
104
     * @param bool   $notInGroup Get groups not in a category
105
     *
106
     * @return array an array with all information about the groups
107
     */
108
    public static function get_group_list(
109
        $categoryId = null,
110
        $course = null,
111
        $status = null,
112
        $sessionId = 0,
113
        $getCount = false,
114
        $filterByKeyword = null,
115
        $returnEntityList = false
116
    ) {
117
        $course = $course ?? api_get_course_entity();
118
119
        if (null === $course) {
120
            return [];
121
        }
122
123
        $sessionId = empty($sessionId) ? api_get_session_id() : (int) $sessionId;
124
        $repo = Container::getGroupRepository();
125
        $session = api_get_session_entity($sessionId);
126
        $qb = $repo->findAllByCourse($course, $session, $filterByKeyword, $status, $categoryId);
127
128
        if ($getCount) {
129
            return $repo->getCount($qb);
130
        }
131
132
        if ($returnEntityList) {
133
            return $qb->getQuery()->getResult();
134
        }
135
136
        return $qb->getQuery()->getArrayResult();
137
138
        /*$table_group = Database::get_course_table(TABLE_GROUP);
139
        $select = ' g.iid,
140
                    g.name,
141
                    g.description,
142
                    g.category_id,
143
                    g.max_student maximum_number_of_members,
144
                    g.secret_directory,
145
                    g.self_registration_allowed,
146
                    g.self_unregistration_allowed,
147
                    g.status
148
                    ';
149
        if ($getCount) {
150
            $select = ' DISTINCT count(g.iid) as count ';
151
        }
152
153
        $sql = "SELECT
154
                $select
155
                FROM $table_group g
156
                WHERE 1 = 1 ";
157
158
        if (!is_null($categoryId)) {
159
            $sql .= " AND g.category_id = '".intval($categoryId)."' ";
160
            $session_condition = api_get_session_condition($sessionId);
161
            if (!empty($session_condition)) {
162
                //$sql .= $session_condition;
163
            }
164
        } else {
165
            $session_condition = api_get_session_condition($sessionId, true);
166
        }
167
168
        $session_condition = '';
169
170
        if (!is_null($status)) {
171
            $sql .= " AND g.status = '".intval($status)."' ";
172
        }
173
174
        //$sql .= " AND g.c_id = $course_id ";
175
        if ($notInGroup) {
176
            $sql .= "  AND (g.category_id IS NULL OR g.category_id = 0) ";
177
        }
178
179
        if (!empty($session_condition)) {
180
            $sql .= $session_condition;
181
        }
182
        $sql .= ' ORDER BY UPPER(g.name)';
183
184
        $result = Database::query($sql);
185
186
        if ($getCount) {
187
            $row = Database::fetch_array($result);
188
189
            return $row['count'];
190
        }
191
192
        $groups = [];
193
        while ($thisGroup = Database::fetch_array($result)) {
194
            $thisGroup['number_of_members'] = count(self::get_subscribed_users($thisGroup));
195
            if (0 != $thisGroup['session_id']) {
196
                $sql = 'SELECT name FROM '.Database::get_main_table(TABLE_MAIN_SESSION).'
197
                        WHERE id='.$thisGroup['session_id'];
198
                $rs_session = Database::query($sql);
199
                if (Database::num_rows($rs_session) > 0) {
200
                    $thisGroup['session_name'] = Database::result($rs_session, 0, 0);
201
                }
202
            }
203
            $groups[] = $thisGroup;
204
        }
205
206
        return $groups;*/
207
    }
208
209
    /**
210
     * Create a group.
211
     *
212
     * @param string $name        The name for this group
213
     * @param int    $category_id
214
     * @param int    $tutor       The user-id of the group's tutor
215
     * @param int    $places      How many people can subscribe to the new group
216
     *
217
     * @return int
218
     */
219
    public static function create_group($name, $category_id, $tutor, $places)
220
    {
221
        $_course = api_get_course_info();
222
        $session_id = api_get_session_id();
223
        $course_id = $_course['real_id'];
224
        $category = self::get_category($category_id);
225
        $places = (int) $places;
226
227
        // Default values
228
        $docState = self::TOOL_PRIVATE;
229
        $calendarState = self::TOOL_PRIVATE;
230
        $workState = self::TOOL_PRIVATE;
231
        $anonuncementState = self::TOOL_PRIVATE;
232
        $forumState = self::TOOL_PRIVATE;
233
        $wikiState = self::TOOL_PRIVATE;
234
        $chatState = self::TOOL_PRIVATE;
235
        $selfRegAllowed = 0;
236
        $selfUnregAllwoed = 0;
237
        $documentAccess = 0;
238
239
        if ($category) {
240
            if (0 == $places) {
241
                //if the amount of users per group is not filled in, use the setting from the category
242
                $places = $category['max_student'];
243
            } else {
244
                if ($places > $category['max_student'] && 0 != $category['max_student']) {
245
                    $places = $category['max_student'];
246
                }
247
            }
248
            $docState = $category['doc_state'];
249
            $calendarState = $category['calendar_state'];
250
            $workState = $category['work_state'];
251
            $anonuncementState = $category['announcements_state'];
252
            $forumState = $category['forum_state'];
253
            $wikiState = $category['wiki_state'];
254
            $chatState = $category['chat_state'];
255
            $selfRegAllowed = $category['self_reg_allowed'];
256
            $selfUnregAllwoed = $category['self_unreg_allowed'];
257
            $documentAccess = isset($category['document_access']) ? $category['document_access'] : 0;
258
        }
259
260
        $course = api_get_course_entity($course_id);
261
        $session = api_get_session_entity($session_id);
262
263
        $category = null;
264
        if (!empty($category_id)) {
265
            $category = Container::getGroupCategoryRepository()->find($category_id);
266
        }
267
268
        $group = new CGroup();
269
        $group
270
            ->setName($name)
271
            ->setCategory($category)
272
            ->setMaxStudent($places)
273
            ->setDocState($docState)
274
            ->setCalendarState($calendarState)
275
            ->setWorkState($workState)
276
            ->setForumState($forumState)
277
            ->setWikiState($wikiState)
278
            ->setAnnouncementsState($anonuncementState)
279
            ->setChatState($chatState)
280
            ->setSelfRegistrationAllowed(1 === (int) $selfRegAllowed)
281
            ->setSelfUnregistrationAllowed(1 === (int) $selfUnregAllwoed)
282
            ->setDocumentAccess((int) $documentAccess)
283
            ->setParent($course)
284
            ->addCourseLink($course, $session)
285
        ;
286
287
        $repo = Container::getGroupRepository();
288
        $repo->create($group);
289
        $lastId = $group->getIid();
290
291
        if ($lastId) {
292
            /*$desired_dir_name = '/'.api_replace_dangerous_char($name).'_groupdocs';
293
294
            $newFolderData = create_unexisting_directory(
295
                $_course,
296
                api_get_user_id(),
297
                $session_id,
298
                $lastId,
299
                null,
300
                null,
301
                    $desired_dir_name,
302
                $desired_dir_name,
303
                1
304
            );*/
305
306
            // create a forum if needed
307
            if ($forumState >= 0) {
308
                $forumName = get_lang('Group forums');
309
                $repo = Container::getForumCategoryRepository();
310
                $category = $repo->findResourceByTitle($forumName, $course->getResourceNode(), $course);
311
                /*$criteria = ['cId' => $course_id, 'catTitle' => $forumName];
312
                $category = $repo->findOneBy($criteria);*/
313
314
                if (empty($category)) {
315
                    $categoryId = store_forumcategory(['forum_category_title' => $forumName]);
316
                } else {
317
                    $categoryId = $category->getIid();
318
                }
319
320
                $values = [];
321
                $values['forum_title'] = $name;
322
                $values['group_id'] = $lastId;
323
                $values['forum_category'] = $categoryId;
324
                $values['allow_anonymous_group']['allow_anonymous'] = 0;
325
                $values['students_can_edit_group']['students_can_edit'] = 0;
326
                $values['approval_direct_group']['approval_direct'] = 0;
327
                $values['allow_attachments_group']['allow_attachments'] = 1;
328
                $values['allow_new_threads_group']['allow_new_threads'] = 1;
329
                $values['default_view_type_group']['default_view_type'] = api_get_setting('default_forum_view');
330
                $values['group_forum'] = $lastId;
331
                if ('1' == $forumState) {
332
                    $values['public_private_group_forum_group']['public_private_group_forum'] = 'public';
333
                } elseif ('2' == $forumState) {
334
                    $values['public_private_group_forum_group']['public_private_group_forum'] = 'private';
335
                } elseif ('0' == $forumState) {
336
                    $values['public_private_group_forum_group']['public_private_group_forum'] = 'unavailable';
337
                }
338
                store_forum($values);
339
            }
340
        }
341
342
        return $lastId;
343
    }
344
345
    /**
346
     * Create subgroups.
347
     * This function creates new groups based on an existing group. It will
348
     * create the specified number of groups and fill those groups with users
349
     * from the base group.
350
     *
351
     * @param int $group_id         the group from which subgroups have to be created
352
     * @param int $number_of_groups The number of groups that have to be created
353
     */
354
    public static function create_subgroups($group_id, $number_of_groups)
355
    {
356
        $courseId = api_get_course_int_id();
357
        $table_group = Database::get_course_table(TABLE_GROUP);
358
        $category_id = self::create_category(
359
            get_lang('Subgroups'),
360
            '',
361
            self::TOOL_PRIVATE,
362
            self::TOOL_PRIVATE,
363
            0,
364
            0,
365
            1,
366
            1
367
        );
368
        $users = self::get_users($group_id);
369
        $group_ids = [];
370
371
        for ($group_nr = 1; $group_nr <= $number_of_groups; $group_nr++) {
372
            $group_ids[] = self::create_group(
373
                get_lang('Subgroup').' '.$group_nr,
374
                $category_id,
375
                0,
376
                0
377
            );
378
        }
379
380
        $members = [];
381
        foreach ($users as $index => $user_id) {
382
            $groupId = $group_ids[$index % $number_of_groups];
383
            self::subscribeUsers(
384
                $user_id,
385
                api_get_group_entity($groupId)
386
            );
387
            $members[$group_ids[$groupId]]++;
388
        }
389
390
        foreach ($members as $group_id => $places) {
391
            $sql = "UPDATE $table_group SET max_student = $places
392
                    WHERE c_id = $courseId  AND id = $group_id";
393
            Database::query($sql);
394
        }
395
    }
396
397
    /**
398
     * Create a group for every class subscribed to the current course.
399
     *
400
     * @param int $categoryId The category in which the groups should be created
401
     *
402
     * @return array
403
     */
404
    public static function create_class_groups($categoryId)
405
    {
406
        $options['where'] = [' usergroup.course_id = ? ' => api_get_course_int_id()];
407
        $obj = new UserGroup();
408
        $classes = $obj->getUserGroupInCourse($options);
409
        $group_ids = [];
410
411
        foreach ($classes as $class) {
412
            $userList = $obj->get_users_by_usergroup($class['id']);
413
            $groupId = self::create_group(
414
                $class['name'],
415
                $categoryId,
416
                0,
417
                null
418
            );
419
420
            if ($groupId) {
421
                self::subscribeUsers($userList, api_get_group_entity($groupId));
422
                $group_ids[] = $groupId;
423
            }
424
        }
425
426
        return $group_ids;
427
    }
428
429
    /**
430
     * Deletes groups and their data.
431
     *
432
     * @author Christophe Gesche <[email protected]>
433
     * @author Hugues Peeters <[email protected]>
434
     * @author Bart Mollet
435
     *
436
     * @param string $course_code Default is current course
437
     *
438
     * @return int - number of groups deleted
439
     */
440
    public static function deleteGroup(CGroup $group, $course_code = null)
441
    {
442
        if (empty($group)) {
443
            return false;
444
        }
445
        $course_info = api_get_course_info($course_code);
446
        if (empty($course_info)) {
447
            return false;
448
        }
449
450
        $em = Database::getManager();
451
        $groupIid = $group->getIid();
452
453
        // Unsubscribe all users
454
        self::unsubscribeAllUsers($groupIid);
455
        self::unsubscribe_all_tutors($groupIid);
456
457
        $em
458
            ->createQuery(
459
                'DELETE FROM ChamiloCourseBundle:CForumForum f WHERE f.forumOfGroup = :group'
460
            )
461
            ->execute(['group' => $groupIid]);
462
463
        // delete the groups
464
        $repo = Container::getGroupRepository();
465
        $em->remove($group);
466
        $em->flush();
467
468
        return true;
469
    }
470
471
    /**
472
     * @deprecated Should be deleted by the resources.
473
     *
474
     * Function needed only when deleting a course, in order to be sure that all group ids are deleted.
475
     *
476
     * @param int $courseId
477
     *
478
     * @return bool
479
     */
480
    public static function deleteAllGroupsFromCourse($courseId)
481
    {
482
        $courseId = (int) $courseId;
483
484
        if (empty($courseId)) {
485
            return false;
486
        }
487
488
        $table = Database::get_course_table(TABLE_GROUP_CATEGORY);
489
        $sql = "SELECT iid FROM $table
490
                WHERE c_id = $courseId ";
491
        Database::query($sql);
492
493
        // Database table definitions
494
        $table = Database::get_course_table(TABLE_GROUP_USER);
495
        $sql = "DELETE FROM $table
496
                WHERE c_id = $courseId";
497
        Database::query($sql);
498
499
        $table = Database::get_course_table(TABLE_GROUP_TUTOR);
500
        $sql = "DELETE FROM $table
501
                WHERE c_id = $courseId";
502
        Database::query($sql);
503
504
        $groupTable = Database::get_course_table(TABLE_GROUP);
505
        $sql = "DELETE FROM $groupTable
506
                WHERE c_id = $courseId";
507
        Database::query($sql);
508
509
        return true;
510
    }
511
512
    /**
513
     * Get group properties.
514
     *
515
     * @param int $group_id the group from which properties are requested
516
     *
517
     * @return array All properties. Array-keys are:
518
     *               name, tutor_id, description, maximum_number_of_students,
519
     *               directory and visibility of tools
520
     */
521
    public static function get_group_properties($group_id)
522
    {
523
        $group_id = (int) $group_id;
524
525
        if (empty($group_id)) {
526
            return null;
527
        }
528
529
        $table_group = Database::get_course_table(TABLE_GROUP);
530
531
        $sql = "SELECT * FROM $table_group
532
                WHERE iid = ".$group_id;
533
534
        $db_result = Database::query($sql);
535
        $db_object = Database::fetch_object($db_result);
536
537
        $result = [];
538
        if ($db_object) {
539
            $result['id'] = $db_object->iid;
540
            $result['iid'] = $db_object->iid;
541
            $result['name'] = $db_object->name;
542
            $result['status'] = $db_object->status;
543
            $result['description'] = $db_object->description;
544
            $result['maximum_number_of_students'] = $db_object->max_student;
545
            $result['max_student'] = $db_object->max_student;
546
            $result['doc_state'] = $db_object->doc_state;
547
            $result['work_state'] = $db_object->work_state;
548
            $result['calendar_state'] = $db_object->calendar_state;
549
            $result['announcements_state'] = $db_object->announcements_state;
550
            $result['forum_state'] = $db_object->forum_state;
551
            $result['wiki_state'] = $db_object->wiki_state;
552
            $result['chat_state'] = $db_object->chat_state;
553
            $result['self_registration_allowed'] = $db_object->self_registration_allowed;
554
            $result['self_unregistration_allowed'] = $db_object->self_unregistration_allowed;
555
            $result['count_users'] = 0;
556
            /*$result['count_users'] = count(
557
                self::get_subscribed_users($result)
558
            );*/
559
            /*$result['count_tutor'] = count(
560
                self::get_subscribed_tutors($result)
561
            );*/
562
            //$result['count_all'] = $result['count_users'] + $result['count_tutor'];
563
            $result['count_all'] = null;
564
            $result['document_access'] = isset($db_object->document_access) ? $db_object->document_access : self::DOCUMENT_MODE_SHARE;
565
        }
566
567
        return $result;
568
    }
569
570
    /**
571
     * @param string $name
572
     * @param string $courseCode
573
     * @param int    $sessionId
574
     *
575
     * @return array
576
     */
577
    public static function getGroupByName($name, $courseCode = null, $sessionId = 0)
578
    {
579
        $name = trim($name);
580
581
        if (empty($name)) {
582
            return [];
583
        }
584
585
        $course_info = api_get_course_info($courseCode);
586
        $course_id = $course_info['real_id'];
587
        $name = Database::escape_string($name);
588
        $sessionId = empty($sessionId) ? api_get_session_id() : (int) $sessionId;
589
        $sessionCondition = api_get_session_condition($sessionId);
590
591
        $table = Database::get_course_table(TABLE_GROUP);
592
        $sql = "SELECT * FROM $table
593
                WHERE
594
                  c_id = $course_id AND
595
                  name = '$name'
596
                  $sessionCondition
597
                LIMIT 1";
598
        $res = Database::query($sql);
599
        $group = [];
600
        if (Database::num_rows($res)) {
601
            $group = Database::fetch_array($res, 'ASSOC');
602
        }
603
604
        return $group;
605
    }
606
607
    /**
608
     * Set group properties
609
     * Changes the group's properties.
610
     *
611
     * @param int       Group Id
612
     * @param string    Group name
613
     * @param string    Group description
614
     * @param int       Max number of students in group
615
     * @param int       Document tool's visibility (0=none,1=private,2=public)
616
     * @param int       Work tool's visibility (0=none,1=private,2=public)
617
     * @param int       Calendar tool's visibility (0=none,1=private,2=public)
618
     * @param int       Announcement tool's visibility (0=none,1=private,2=public)
619
     * @param int       Forum tool's visibility (0=none,1=private,2=public)
620
     * @param int       Wiki tool's visibility (0=none,1=private,2=public)
621
     * @param int       Chat tool's visibility (0=none,1=private,2=public)
622
     * @param bool Whether self registration is allowed or not
623
     * @param bool Whether self unregistration is allowed or not
624
     * @param int $categoryId
625
     * @param int $documentAccess
626
     *
627
     * @return bool TRUE if properties are successfully changed, false otherwise
628
     */
629
    public static function set_group_properties(
630
        $group_id,
631
        $name,
632
        $description,
633
        $maxStudent,
634
        $docState,
635
        $workState,
636
        $calendarState,
637
        $anonuncementState,
638
        $forumState,
639
        $wikiState,
640
        $chatState,
641
        $selfRegistrationAllowed,
642
        $selfUnRegistrationAllowed,
643
        $categoryId = null,
644
        $documentAccess = 0
645
    ) {
646
        $table_forum = Database::get_course_table(TABLE_FORUM);
647
        $categoryId = (int) $categoryId;
648
        $group_id = (int) $group_id;
649
        $forumState = (int) $forumState;
650
        $repo = Container::getGroupRepository();
651
652
        /** @var CGroup $group */
653
        $group = $repo->find($group_id);
654
655
        $category = null;
656
        if (!empty($categoryId)) {
657
            $category = Container::getGroupCategoryRepository()->find($categoryId);
658
        }
659
660
        $group
661
            ->setName($name)
662
            ->setCategory($category)
663
            ->setMaxStudent($maxStudent)
664
            ->setDocState($docState)
665
            ->setCalendarState($calendarState)
666
            ->setWorkState($workState)
667
            ->setForumState($forumState)
668
            ->setWikiState($wikiState)
669
            ->setAnnouncementsState($anonuncementState)
670
            ->setChatState($chatState)
671
            ->setSelfRegistrationAllowed($selfRegistrationAllowed)
672
            ->setSelfUnregistrationAllowed($selfUnRegistrationAllowed)
673
            ->setDocumentAccess($documentAccess)
674
        ;
675
676
        $repo->update($group);
677
678
        /* Here we are updating a field in the table forum_forum that perhaps
679
        duplicates the table group_info.forum_state cvargas*/
680
        $sql2 = "UPDATE $table_forum SET ";
681
        if (1 === $forumState) {
682
            $sql2 .= " forum_group_public_private='public' ";
683
        } elseif (2 === $forumState) {
684
            $sql2 .= " forum_group_public_private='private' ";
685
        } elseif (0 === $forumState) {
686
            $sql2 .= " forum_group_public_private='unavailable' ";
687
        }
688
        $sql2 .= ' WHERE forum_of_group='.$group_id;
689
        Database::query($sql2);
690
691
        return true;
692
    }
693
694
    /**
695
     * Get the total number of groups for the current course.
696
     *
697
     * @return int the number of groups for the current course
698
     */
699
    public static function get_number_of_groups()
700
    {
701
        $repo = Container::getGroupRepository();
702
703
        $course = api_get_course_entity(api_get_course_int_id());
704
        if (null === $course) {
705
            return 0;
706
        }
707
708
        $session = api_get_session_entity(api_get_session_id());
709
        $group = api_get_group_entity(api_get_group_id());
710
        $qb = $repo->getResourcesByCourse($course, $session, $group);
711
        $qb->select('count(resource)');
712
713
        return $qb->getQuery()->getSingleScalarResult();
714
        /*$courseId = api_get_course_int_id();
715
        $table = Database::get_course_table(TABLE_GROUP);
716
        $sql = "SELECT COUNT(id) AS number_of_groups
717
                FROM $table
718
                WHERE c_id = $courseId ";
719
        $res = Database::query($sql);
720
        $obj = Database::fetch_object($res);
721
722
        return $obj->number_of_groups;*/
723
    }
724
725
    /**
726
     * Get all categories.
727
     */
728
    public static function get_categories(Course $course = null): array
729
    {
730
        $repo = Container::getGroupCategoryRepository();
731
732
        if (null === $course) {
733
            $course = api_get_course_entity(api_get_course_int_id());
734
        }
735
736
        $session = api_get_session_entity(api_get_session_id());
737
        //$group = api_get_group_entity(api_get_group_id());
738
        $group = null;
739
740
        $qb = $repo->getResourcesByCourse($course, $session, $group);
741
742
        return $qb->getQuery()->getArrayResult();
743
        /*$course_info = api_get_course_info($course_code);
744
        $courseId = $course_info['real_id'];
745
        $table = Database::get_course_table(TABLE_GROUP_CATEGORY);
746
        $sql = "SELECT * FROM $table
747
                WHERE c_id = $courseId
748
                ORDER BY display_order";
749
        $res = Database::query($sql);
750
        $cats = [];
751
        while ($cat = Database::fetch_array($res)) {
752
            $cats[] = $cat;
753
        }
754
755
        return $cats;*/
756
    }
757
758
    /**
759
     * Get a group category.
760
     *
761
     * @param int    $id          The category id
762
     * @param string $course_code The course (default = current course)
763
     *
764
     * @return array
765
     */
766
    public static function get_category($id, $course_code = null)
767
    {
768
        if (empty($id)) {
769
            return [];
770
        }
771
772
        $courseInfo = api_get_course_info($course_code);
773
        $courseId = $courseInfo['real_id'];
774
        $id = (int) $id;
775
        $table = Database::get_course_table(TABLE_GROUP_CATEGORY);
776
        $sql = "SELECT * FROM $table
777
                WHERE  iid = $id
778
                LIMIT 1";
779
        $res = Database::query($sql);
780
781
        return Database::fetch_array($res);
782
    }
783
784
    /**
785
     * Get a group category.
786
     *
787
     * @param string $title
788
     * @param string $course_code The course (default = current course)
789
     *
790
     * @return array
791
     */
792
    public static function getCategoryByTitle($title, $course_code = null)
793
    {
794
        $title = trim($title);
795
796
        if (empty($title)) {
797
            return [];
798
        }
799
800
        $course_info = api_get_course_info($course_code);
801
        $courseId = $course_info['real_id'];
802
        $title = Database::escape_string($title);
803
        $table = Database::get_course_table(TABLE_GROUP_CATEGORY);
804
        $sql = "SELECT * FROM $table
805
                WHERE c_id = $courseId AND title = '$title'
806
                LIMIT 1";
807
        $res = Database::query($sql);
808
        $category = [];
809
        if (Database::num_rows($res)) {
810
            $category = Database::fetch_array($res, 'ASSOC');
811
        }
812
813
        return $category;
814
    }
815
816
    /**
817
     * Get the unique category of a given group.
818
     *
819
     * @param int    $group_id    The iid of the group
820
     * @param string $course_code The course in which the group is (default =
821
     *                            current course)
822
     *
823
     * @return array The category
824
     */
825
    public static function get_category_from_group($group_id, $course_code = '')
826
    {
827
        $table_group = Database::get_course_table(TABLE_GROUP);
828
        $table_group_cat = Database::get_course_table(TABLE_GROUP_CATEGORY);
829
830
        $group_id = (int) $group_id;
831
832
        if (empty($group_id)) {
833
            return [];
834
        }
835
836
        $course_info = api_get_course_info($course_code);
837
838
        if (empty($course_info)) {
839
            return false;
840
        }
841
842
        $sql = "SELECT gc.* FROM $table_group_cat gc
843
                INNER JOIN $table_group g
844
                ON (gc.iid = g.category_id)
845
                WHERE
846
                    g.iid = $group_id
847
                LIMIT 1";
848
        $res = Database::query($sql);
849
        $cat = [];
850
        if (Database::num_rows($res)) {
851
            $cat = Database::fetch_array($res);
852
        }
853
854
        return $cat;
855
    }
856
857
    /**
858
     * Delete a group category.
859
     *
860
     * @param int    $cat_id      The id of the category to delete
861
     * @param string $course_code The code in which the category should be
862
     *                            deleted (default = current course)
863
     *
864
     * @return bool
865
     */
866
    public static function delete_category($cat_id, $course_code = '')
867
    {
868
        $course_info = api_get_course_info($course_code);
869
        if (empty($course_info)) {
870
            return false;
871
        }
872
        $course_id = $course_info['real_id'];
873
874
        $table_group = Database::get_course_table(TABLE_GROUP);
875
        $table_group_cat = Database::get_course_table(TABLE_GROUP_CATEGORY);
876
        $cat_id = (int) $cat_id;
877
        $sql = "SELECT iid FROM $table_group
878
                WHERE category_id='".$cat_id."'";
879
        $res = Database::query($sql);
880
        if (Database::num_rows($res) > 0) {
881
            while ($group = Database::fetch_object($res)) {
882
                // Delete all groups in category
883
                /*$groupInfo = self::get_group_properties($group->iid, true);
884
                self::deleteGroup($groupInfo, $course_code);
885
                */
886
                // Set the category to NULL to avoid losing groups in sessions.
887
                $sql = "UPDATE $table_group SET category_id = NULL WHERE iid = ".$group->iid;
888
                Database::query($sql);
889
            }
890
        }
891
892
        $category = Database::getManager()->getRepository(CGroupCategory::class)->find($cat_id);
893
        if ($category) {
894
            Database::getManager()->remove($category);
895
            Database::getManager()->flush();
896
        }
897
898
        /*$sql = "DELETE FROM $table_group_cat
899
                WHERE iid='".$cat_id."'";
900
        Database::query($sql);*/
901
902
        return true;
903
    }
904
905
    /**
906
     * Create group category.
907
     *
908
     * @param string $title                     The title of the new category
909
     * @param string $description               The description of the new category
910
     * @param int    $selfRegistrationAllowed   allow users to self register
911
     * @param int    $selfUnRegistrationAllowed allow user to self unregister
912
     * @param int    $documentAccess            document access
913
     *
914
     * @return mixed
915
     */
916
    public static function create_category(
917
        $title,
918
        $description,
919
        $docState,
920
        $workState,
921
        $calendarState,
922
        $anonuncementState,
923
        $forumState,
924
        $wikiState,
925
        $chatState = 1,
926
        $selfRegistrationAllowed = 0,
927
        $selfUnRegistrationAllowed = 0,
928
        $maxStudent = 8,
929
        $groupsPerUser = 0,
930
        $documentAccess = 0
931
    ) {
932
        if (empty($title)) {
933
            return false;
934
        }
935
        /*$sql = "SELECT MAX(display_order)+1 as new_order
936
                FROM $table
937
                WHERE c_id = $course_id ";
938
        $res = Database::query($sql);
939
        $obj = Database::fetch_object($res);
940
        if (!isset($obj->new_order)) {
941
            $obj->new_order = 1;
942
        }*/
943
944
        $course = api_get_course_entity(api_get_course_int_id());
945
        $session = api_get_session_entity(api_get_session_id());
946
947
        $category = new CGroupCategory();
948
        $category
949
            ->setTitle($title)
950
            ->setDescription($description)
951
            ->setMaxStudent($maxStudent)
952
            ->setDocState($docState)
953
            ->setCalendarState($calendarState)
954
            ->setWorkState($workState)
955
            ->setForumState($forumState)
956
            ->setWikiState($wikiState)
957
            ->setAnnouncementsState($anonuncementState)
958
            ->setChatState($chatState)
959
            ->setSelfRegAllowed($selfRegistrationAllowed)
960
            ->setSelfUnregAllowed($selfUnRegistrationAllowed)
961
            ->setDocumentAccess($documentAccess)
962
            ->setGroupsPerUser($groupsPerUser)
963
            ->setParent($course)
964
            ->addCourseLink($course, $session)
965
        ;
966
967
        $repo = Container::getGroupCategoryRepository();
968
        $repo->create($category);
969
970
        return $category->getIid();
971
    }
972
973
    /**
974
     * Update group category.
975
     *
976
     * @param int    $id
977
     * @param string $title
978
     * @param string $description
979
     * @param $doc_state
980
     * @param $work_state
981
     * @param $calendar_state
982
     * @param $announcements_state
983
     * @param $forum_state
984
     * @param $wiki_state
985
     * @param $chat_state
986
     * @param $selfRegistrationAllowed
987
     * @param $selfUnRegistrationAllowed
988
     * @param $maximum_number_of_students
989
     * @param $groups_per_user
990
     * @param $documentAccess
991
     */
992
    public static function update_category(
993
        $id,
994
        $title,
995
        $description,
996
        $doc_state,
997
        $work_state,
998
        $calendar_state,
999
        $announcements_state,
1000
        $forum_state,
1001
        $wiki_state,
1002
        $chat_state,
1003
        $selfRegistrationAllowed,
1004
        $selfUnRegistrationAllowed,
1005
        $maximum_number_of_students,
1006
        $groups_per_user,
1007
        $documentAccess
1008
    ) {
1009
        $table = Database::get_course_table(TABLE_GROUP_CATEGORY);
1010
        $id = (int) $id;
1011
1012
        $allowDocumentAccess = api_get_configuration_value('group_category_document_access');
1013
        $documentCondition = '';
1014
        if ($allowDocumentAccess) {
1015
            $documentAccess = (int) $documentAccess;
1016
            $documentCondition = " document_access = $documentAccess, ";
1017
        }
1018
1019
        $sql = 'UPDATE '.$table." SET
1020
                    title='".Database::escape_string($title)."',
1021
                    description='".Database::escape_string($description)."',
1022
                    doc_state = '".Database::escape_string($doc_state)."',
1023
                    work_state = '".Database::escape_string($work_state)."',
1024
                    calendar_state = '".Database::escape_string($calendar_state)."',
1025
                    announcements_state = '".Database::escape_string($announcements_state)."',
1026
                    forum_state = '".Database::escape_string($forum_state)."',
1027
                    wiki_state = '".Database::escape_string($wiki_state)."',
1028
                    chat_state = '".Database::escape_string($chat_state)."',
1029
                    groups_per_user   = '".Database::escape_string($groups_per_user)."',
1030
                    self_reg_allowed = '".Database::escape_string($selfRegistrationAllowed)."',
1031
                    self_unreg_allowed = '".Database::escape_string($selfUnRegistrationAllowed)."',
1032
                    $documentCondition
1033
                    max_student = ".intval($maximum_number_of_students)."
1034
                WHERE iid = $id";
1035
        Database::query($sql);
1036
1037
        // Updating all groups inside this category
1038
        $groups = self::get_group_list($id);
1039
1040
        if (!empty($groups)) {
1041
            foreach ($groups as $group) {
1042
                self::set_group_properties(
1043
                    $group['iid'],
1044
                    $group['name'],
1045
                    $group['description'],
1046
                    $maximum_number_of_students,
1047
                    $doc_state,
1048
                    $work_state,
1049
                    $calendar_state,
1050
                    $announcements_state,
1051
                    $forum_state,
1052
                    $wiki_state,
1053
                    $chat_state,
1054
                    $selfRegistrationAllowed,
1055
                    $selfUnRegistrationAllowed,
1056
                    $id,
1057
                    $documentAccess
1058
                );
1059
            }
1060
        }
1061
    }
1062
1063
    /**
1064
     * Returns the number of groups of the user with the greatest number of
1065
     * subscriptions in the given category.
1066
     */
1067
    public static function get_current_max_groups_per_user($category_id = null, $course_code = null)
1068
    {
1069
        $course_info = api_get_course_info($course_code);
1070
        $group_table = Database::get_course_table(TABLE_GROUP);
1071
1072
        $group_user_table = Database::get_course_table(TABLE_GROUP_USER);
1073
        $sql = "SELECT COUNT(gu.group_id) AS current_max
1074
                FROM $group_user_table gu
1075
                INNER JOIN $group_table g
1076
                ON (gu.group_id = g.iid)
1077
                WHERE 1= 1 ";
1078
        if (null != $category_id) {
1079
            $category_id = intval($category_id);
1080
            $sql .= ' AND g.category_id = '.$category_id;
1081
        }
1082
        $sql .= ' GROUP BY gu.user_id
1083
                  ORDER BY current_max DESC LIMIT 1';
1084
1085
        $res = Database::query($sql);
1086
        $obj = Database::fetch_object($res);
1087
1088
        if ($obj) {
1089
            return $obj->current_max;
1090
        }
1091
1092
        return 0;
1093
    }
1094
1095
    /**
1096
     * Swaps the display-order of two categories.
1097
     *
1098
     * @param int $id1 The id of the first category
1099
     * @param int $id2 The id of the second category
1100
     */
1101
    public static function swap_category_order($id1, $id2)
1102
    {
1103
        $table = Database::get_course_table(TABLE_GROUP_CATEGORY);
1104
        $id1 = intval($id1);
1105
        $id2 = intval($id2);
1106
        $course_id = api_get_course_int_id();
1107
1108
        $sql = "SELECT id, display_order FROM $table
1109
                WHERE id IN ($id1,$id2) AND c_id = $course_id ";
1110
        $res = Database::query($sql);
1111
        $cat1 = Database::fetch_object($res);
1112
        $cat2 = Database::fetch_object($res);
1113
        if ($cat1 && $cat2) {
1114
            $sql = "UPDATE $table SET display_order=$cat2->display_order
1115
                    WHERE id = $cat1->id AND c_id = $course_id ";
1116
            Database::query($sql);
1117
1118
            $sql = "UPDATE $table SET display_order=$cat1->display_order
1119
                    WHERE id = $cat2->id AND c_id = $course_id ";
1120
            Database::query($sql);
1121
        }
1122
    }
1123
1124
    /**
1125
     * Get all users from a given group.
1126
     *
1127
     * @param int  $group_id        The group
1128
     * @param bool $load_extra_info
1129
     * @param int  $start
1130
     * @param int  $limit
1131
     * @param bool $getCount
1132
     * @param int  $courseId
1133
     * @param $column
1134
     * @param $direction
1135
     *
1136
     * @return array list of user id
1137
     */
1138
    public static function get_users(
1139
        $group_id,
1140
        $load_extra_info = false,
1141
        $start = null,
1142
        $limit = null,
1143
        $getCount = false,
1144
        $courseId = null,
1145
        $column = null,
1146
        $direction = null
1147
    ) {
1148
        $group_user_table = Database::get_course_table(TABLE_GROUP_USER);
1149
        $groupTable = Database::get_course_table(TABLE_GROUP);
1150
        $user_table = Database::get_main_table(TABLE_MAIN_USER);
1151
        $group_id = (int) $group_id;
1152
1153
        if (empty($courseId)) {
1154
            $courseId = api_get_course_int_id();
1155
        } else {
1156
            $courseId = (int) $courseId;
1157
        }
1158
1159
        $select = ' SELECT u.id, firstname, lastname ';
1160
        if ($getCount) {
1161
            $select = ' SELECT count(u.id) count';
1162
        }
1163
        $sql = "$select
1164
                FROM $group_user_table gu
1165
                INNER JOIN $groupTable g
1166
                ON (gu.group_id = g.iid)
1167
                INNER JOIN $user_table u
1168
                ON (u.id = gu.user_id)
1169
                WHERE
1170
                    g.iid = $group_id";
1171
1172
        if (!empty($column) && !empty($direction)) {
1173
            $column = Database::escape_string($column, null, false);
1174
            $direction = ('ASC' == $direction ? 'ASC' : 'DESC');
1175
            $sql .= " ORDER BY $column $direction";
1176
        }
1177
1178
        if (!empty($start) && !empty($limit)) {
1179
            $start = (int) $start;
1180
            $limit = (int) $limit;
1181
            $sql .= " LIMIT $start, $limit";
1182
        }
1183
        $res = Database::query($sql);
1184
        $users = [];
1185
        while ($obj = Database::fetch_object($res)) {
1186
            if ($getCount) {
1187
                return $obj->count;
1188
                break;
0 ignored issues
show
Unused Code introduced by
break is not strictly necessary here and could be removed.

The break statement is not necessary if it is preceded for example by a return statement:

switch ($x) {
    case 1:
        return 'foo';
        break; // This break is not necessary and can be left off.
}

If you would like to keep this construct to be consistent with other case statements, you can safely mark this issue as a false-positive.

Loading history...
1189
            }
1190
            if ($load_extra_info) {
1191
                $users[] = api_get_user_info($obj->id);
1192
            } else {
1193
                $users[] = $obj->id;
1194
            }
1195
        }
1196
1197
        return $users;
1198
    }
1199
1200
    /**
1201
     * @param int $group_id id
1202
     *
1203
     * @return array
1204
     */
1205
    public static function getStudentsAndTutors($group_id)
1206
    {
1207
        $group_user_table = Database::get_course_table(TABLE_GROUP_USER);
1208
        $tutor_user_table = Database::get_course_table(TABLE_GROUP_TUTOR);
1209
        $groupTable = Database::get_course_table(TABLE_GROUP);
1210
1211
        $course_id = api_get_course_int_id();
1212
        $group_id = (int) $group_id;
1213
1214
        $sql = "SELECT user_id
1215
                FROM $group_user_table gu
1216
                INNER JOIN $groupTable g
1217
                ON (gu.group_id = g.iid)
1218
                WHERE g.iid = $group_id";
1219
        $res = Database::query($sql);
1220
        $users = [];
1221
1222
        while ($obj = Database::fetch_object($res)) {
1223
            $users[] = api_get_user_info($obj->user_id);
1224
        }
1225
1226
        $sql = "SELECT user_id
1227
                FROM $tutor_user_table gu
1228
                INNER JOIN $groupTable g
1229
                ON (gu.group_id = g.iid)
1230
                WHERE g.iid = $group_id";
1231
        $res = Database::query($sql);
1232
        while ($obj = Database::fetch_object($res)) {
1233
            $users[] = api_get_user_info($obj->user_id);
1234
        }
1235
1236
        return $users;
1237
    }
1238
1239
    /**
1240
     * Get only tutors from a group.
1241
     *
1242
     * @param array $groupInfo
1243
     *
1244
     * @return array
1245
     */
1246
    public static function getTutors($groupInfo)
1247
    {
1248
        $groupTable = Database::get_course_table(TABLE_GROUP);
1249
        $tutor_user_table = Database::get_course_table(TABLE_GROUP_TUTOR);
1250
        $course_id = api_get_course_int_id();
1251
        $group_id = (int) $groupInfo['iid'];
1252
1253
        $sql = "SELECT user_id
1254
                FROM $tutor_user_table gu
1255
                INNER JOIN $groupTable g
1256
                ON (gu.group_id = g.iid)
1257
                WHERE g.iid = $group_id";
1258
        $res = Database::query($sql);
1259
1260
        $users = [];
1261
        while ($obj = Database::fetch_object($res)) {
1262
            $users[] = api_get_user_info($obj->user_id);
1263
        }
1264
1265
        return $users;
1266
    }
1267
1268
    /**
1269
     * Get only students from a group (not tutors).
1270
     *
1271
     * @param bool $filterOnlyActive
1272
     *
1273
     * @return array
1274
     */
1275
    public static function getStudents($groupId, $filterOnlyActive = false)
1276
    {
1277
        $groupId = (int) $groupId;
1278
        $activeCondition = $filterOnlyActive ? 'AND u.active = 1' : '';
1279
1280
        $em = Database::getManager();
1281
        $subscriptions = $em
1282
            ->createQuery("
1283
                SELECT u.id FROM ChamiloCoreBundle:User u
1284
                INNER JOIN ChamiloCourseBundle:CGroupRelUser gu
1285
                WITH u.id = gu.user
1286
                INNER JOIN ChamiloCourseBundle:CGroup g
1287
                WITH gu.group = g.iid
1288
                WHERE g.iid = :group
1289
                    $activeCondition
1290
            ")
1291
            ->setParameters([
1292
                'group' => $groupId,
1293
            ])
1294
            ->getResult();
1295
1296
        $users = [];
1297
        if (!empty($subscriptions)) {
1298
            foreach ($subscriptions as $subscription) {
1299
                $users[] = api_get_user_info($subscription['id']);
1300
            }
1301
        }
1302
1303
        return $users;
1304
    }
1305
1306
    public static function getStudentsCount($groupId, $filterOnlyActive = false)
1307
    {
1308
        $groupId = (int) $groupId;
1309
        $activeCondition = $filterOnlyActive ? 'AND u.active = 1' : '';
1310
1311
        $em = Database::getManager();
1312
1313
        return $em
1314
            ->createQuery("
1315
                SELECT COUNT(u.id) FROM ChamiloCoreBundle:User u
1316
                INNER JOIN ChamiloCourseBundle:CGroupRelUser gu
1317
                WITH u.id = gu.user
1318
                INNER JOIN ChamiloCourseBundle:CGroup g
1319
                WITH gu.group = g.iid
1320
                WHERE g.iid = :group
1321
                    $activeCondition
1322
            ")
1323
            ->setParameters([
1324
                'group' => $groupId,
1325
            ])
1326
            ->getSingleScalarResult();
1327
    }
1328
1329
    /**
1330
     * Returns users belonging to any of the group.
1331
     *
1332
     * @param array $groups list of group ids
1333
     *
1334
     * @return array list of user ids
1335
     */
1336
    public static function get_groups_users($groups = [])
1337
    {
1338
        $result = [];
1339
        $table = Database::get_course_table(TABLE_GROUP_USER);
1340
        $groups = array_map('intval', $groups);
1341
        // protect individual elements with surrounding quotes
1342
        $groups = implode(', ', $groups);
1343
        $sql = "SELECT DISTINCT user_id
1344
                FROM $table gu
1345
                WHERE gu.group_id IN ($groups)";
1346
        $rs = Database::query($sql);
1347
        while ($row = Database::fetch_array($rs)) {
1348
            $result[] = $row['user_id'];
1349
        }
1350
1351
        return $result;
1352
    }
1353
1354
    /**
1355
     * Fill the groups with students.
1356
     * The algorithm takes care to first fill the groups with the least # of users.
1357
     * Analysis
1358
     * There was a problem with the "ALL" setting.
1359
     * When max # of groups is set to all, the value is sometimes NULL and sometimes ALL
1360
     * and in both cased the query does not work as expected.
1361
     * Stupid solution (currently implemented: set ALL to a big number (INFINITE) and things are solved :)
1362
     * Better solution: that's up to you.
1363
     *
1364
     * Note
1365
     * Throughout Dokeos there is some confusion about "course id" and "course code"
1366
     * The code is e.g. TEST101, but sometimes a variable that is called courseID also contains a course code string.
1367
     * However, there is also a integer course_id that uniquely identifies the course.
1368
     * ywarnier:> Now the course_id has been removed (25/1/2005)
1369
     * The databases are als very inconsistent in this.
1370
     *
1371
     * @author Chrisptophe Gesche <[email protected]>,
1372
     *         Hugues Peeters     <[email protected]> - original version
1373
     * @author Roan Embrechts - virtual course support, code cleaning
1374
     * @author Bart Mollet - code cleaning, use other GroupManager-functions
1375
     *
1376
     * @return bool
1377
     */
1378
    public static function fillGroupWithUsers(CGroup $group)
1379
    {
1380
        $_course = api_get_course_info();
1381
        if (empty($_course) || empty($group)) {
1382
            return false;
1383
        }
1384
        $session_id = api_get_session_id();
1385
        $complete_user_list = CourseManager::get_user_list_from_course_code(
1386
            $_course['code'],
1387
            $session_id
1388
        );
1389
        $groupIid = $group->getIid();
1390
        $category = self::get_category_from_group($groupIid);
1391
1392
        // Getting max numbers of user from group
1393
        $maxNumberStudents = empty($group->getMaxStudent()) ? self::INFINITE : $group->getMaxStudent();
1394
        $groupsPerUser = self::INFINITE;
1395
        $categoryId = 0;
1396
        if ($category) {
1397
            $groupsPerUser = empty($category['groups_per_user']) ? self::INFINITE : $category['groups_per_user'];
1398
            $maxNumberStudentsCategory = empty($category['max_student']) ? self::INFINITE : $category['max_student'];
1399
            $categoryId = $category['iid'];
1400
            if ($maxNumberStudentsCategory < $maxNumberStudents) {
1401
                $maxNumberStudents = $maxNumberStudentsCategory;
1402
            }
1403
        }
1404
1405
        $usersToAdd = [];
1406
        foreach ($complete_user_list as $userInfo) {
1407
            $isSubscribed = self::is_subscribed($userInfo['user_id'], $group);
1408
            if ($isSubscribed) {
1409
                continue;
1410
            }
1411
            $numberOfGroups = self::user_in_number_of_groups(
1412
                $userInfo['user_id'],
1413
                $categoryId
1414
            );
1415
            if ($groupsPerUser > $numberOfGroups) {
1416
                $usersToAdd[] = $userInfo['user_id'];
1417
            }
1418
            if (count($usersToAdd) == $maxNumberStudents) {
1419
                break;
1420
            }
1421
        }
1422
1423
        foreach ($usersToAdd as $userId) {
1424
            self::subscribeUsers($userId, $group);
1425
        }
1426
    }
1427
1428
    /**
1429
     * Get the number of students in a group.
1430
     *
1431
     * @param int $group_id id
1432
     *
1433
     * @return int number of students in the given group
1434
     */
1435
    public static function number_of_students($group_id, $course_id = null)
1436
    {
1437
        $table = Database::get_course_table(TABLE_GROUP_USER);
1438
        $group_id = (int) $group_id;
1439
        $course_id = (int) $course_id;
1440
1441
        if (empty($course_id)) {
1442
            $course_id = api_get_course_int_id();
1443
        }
1444
        $sql = "SELECT COUNT(*) AS number_of_students
1445
                FROM $table
1446
                WHERE c_id = $course_id AND group_id = $group_id";
1447
        $result = Database::query($sql);
1448
        $db_object = Database::fetch_object($result);
1449
1450
        return $db_object->number_of_students;
1451
    }
1452
1453
    /**
1454
     * Maximum number of students in a group.
1455
     *
1456
     * @param int $group_id iid
1457
     *
1458
     * @return int maximum number of students in the given group
1459
     */
1460
    public static function maximum_number_of_students($group_id)
1461
    {
1462
        $table = Database::get_course_table(TABLE_GROUP);
1463
        $group_id = (int) $group_id;
1464
        $course_id = api_get_course_int_id();
1465
        $sql = "SELECT max_student FROM $table
1466
                WHERE iid = $group_id";
1467
        $db_result = Database::query($sql);
1468
        $db_object = Database::fetch_object($db_result);
1469
        if (0 == $db_object->max_student) {
1470
            return self::INFINITE;
1471
        }
1472
1473
        return $db_object->max_student;
1474
    }
1475
1476
    /**
1477
     * Number of groups of a user.
1478
     *
1479
     * @param int $user_id
1480
     * @param int $cat_id
1481
     *
1482
     * @return int the number of groups the user is subscribed in
1483
     */
1484
    public static function user_in_number_of_groups($user_id, $cat_id = 0)
1485
    {
1486
        $table_group_user = Database::get_course_table(TABLE_GROUP_USER);
1487
        $table_group = Database::get_course_table(TABLE_GROUP);
1488
        $user_id = (int) $user_id;
1489
        $cat_id = (int) $cat_id;
1490
1491
        $course_id = api_get_course_int_id();
1492
        $cat_condition = '';
1493
        if (!empty($cat_id)) {
1494
            $cat_condition = " AND g.category_id =  $cat_id ";
1495
        }
1496
1497
        $sql = "SELECT COUNT(*) AS number_of_groups
1498
                FROM $table_group_user gu
1499
                INNER JOIN $table_group g
1500
                ON (g.iid = gu.group_id)
1501
                WHERE
1502
                    gu.user_id = $user_id
1503
                    $cat_condition";
1504
1505
        $result = Database::query($sql);
1506
        $db_object = Database::fetch_object($result);
1507
1508
        return $db_object->number_of_groups;
1509
    }
1510
1511
    /**
1512
     * Is sef-registration allowed?
1513
     *
1514
     * @param int $user_id
1515
     *
1516
     * @return bool TRUE if self-registration is allowed in the given group
1517
     */
1518
    public static function is_self_registration_allowed($user_id, CGroup $group)
1519
    {
1520
        if (empty($user_id)) {
1521
            return false;
1522
        }
1523
1524
        if ($group) {
1525
            if (0 == $group->getStatus() || 1 != $group->getSelfRegistrationAllowed()) {
1526
                return false;
1527
            }
1528
1529
            return self::canUserSubscribe($user_id, $group);
1530
        }
1531
1532
        return false;
1533
    }
1534
1535
    /**
1536
     * Is sef-unregistration allowed?
1537
     *
1538
     * @param int $user_id
1539
     *
1540
     * @return bool TRUE if self-unregistration is allowed in the given group
1541
     */
1542
    public static function is_self_unregistration_allowed($user_id, CGroup $group)
1543
    {
1544
        if (empty($user_id) || empty($group)) {
1545
            return false;
1546
        }
1547
        if (0 == $group->getStatus() || 1 != $group->getSelfUnregistrationAllowed()) {
1548
            return false;
1549
        }
1550
1551
        return self::is_subscribed($user_id, $group);
1552
    }
1553
1554
    /**
1555
     * Is user subscribed in group?
1556
     *
1557
     * @param int $user_id
1558
     *
1559
     * @return bool TRUE if given user is subscribed in given group
1560
     */
1561
    public static function is_subscribed($user_id, CGroup $group)
1562
    {
1563
        $course_id = api_get_course_int_id();
1564
        if (empty($user_id) || empty($group) || empty($course_id)) {
1565
            return false;
1566
        }
1567
        $table = Database::get_course_table(TABLE_GROUP_USER);
1568
        $group_id = $group->getIid();
1569
        $user_id = (int) $user_id;
1570
1571
        $sql = "SELECT 1 FROM $table
1572
                WHERE
1573
                    group_id = $group_id AND
1574
                    user_id = $user_id
1575
                ";
1576
        $result = Database::query($sql);
1577
1578
        return Database::num_rows($result) > 0;
1579
    }
1580
1581
    /**
1582
     * Can a user subscribe to a specified group in a course.
1583
     *
1584
     * @param int  $user_id
1585
     * @param bool $checkMaxNumberStudents
1586
     *
1587
     * @return bool true if success
1588
     */
1589
    public static function canUserSubscribe(
1590
        $user_id,
1591
        CGroup $group,
1592
        $checkMaxNumberStudents = true
1593
    ) {
1594
        $groupIid = $group->getIid();
1595
        if ($checkMaxNumberStudents) {
1596
            $category = self::get_category_from_group($group->getIid());
1597
            if ($category) {
1598
                if (self::GROUP_PER_MEMBER_NO_LIMIT == $category['groups_per_user']) {
1599
                    $category['groups_per_user'] = self::INFINITE;
1600
                }
1601
                $result = self::user_in_number_of_groups($user_id, $category['iid']) < $category['groups_per_user'];
1602
                if (false == $result) {
1603
                    return false;
1604
                }
1605
            }
1606
1607
            $result = self::number_of_students($groupIid) < self::maximum_number_of_students($groupIid);
1608
1609
            if (false == $result) {
1610
                return false;
1611
            }
1612
        }
1613
1614
        $result = self::isTutorOfGroup($user_id, $group);
1615
1616
        if ($result) {
1617
            return false;
1618
        }
1619
1620
        $result = self::is_subscribed($user_id, $group);
1621
1622
        if ($result) {
1623
            return false;
1624
        }
1625
1626
        return true;
1627
    }
1628
1629
    /**
1630
     * Get all subscribed users (members) from a group.
1631
     *
1632
     * @return array An array with information of all users from the given group.
1633
     *               (user_id, firstname, lastname, email)
1634
     */
1635
    public static function get_subscribed_users(CGroup $group)
1636
    {
1637
        //$order = api_sort_by_first_name() ? ' ORDER BY u.firstname, u.lastname' : ' ORDER BY u.lastname, u.firstname';
1638
        $order = ['lastname'=> Criteria::DESC, 'firstname'=> Criteria::ASC];
1639
        if (api_sort_by_first_name()) {
1640
            $order = ['firstname' => Criteria::ASC, 'lastname' => Criteria::ASC];
1641
        }
1642
        $orderListByOfficialCode = api_get_setting('order_user_list_by_official_code');
1643
        if ('true' === $orderListByOfficialCode) {
1644
            //$order = ' ORDER BY u.official_code, u.firstname, u.lastname';
1645
            $order = ['officialCode' => Criteria::ASC, 'firstname' => Criteria::ASC, 'lastname' => Criteria::ASC];
1646
        }
1647
1648
        $users = $group->getMembers();
1649
        $userList = [];
1650
        foreach ($users as $groupRelUser) {
1651
            $userList[] = $groupRelUser->getUser();
1652
        }
1653
1654
        $criteria = Criteria::create();
1655
        $criteria->orderBy($order);
1656
        $users = new ArrayCollection($userList);
1657
        $users = $users->matching($criteria);
1658
1659
        $list = [];
1660
        foreach ($users as $user) {
1661
            $list[$user->getId()] = [
1662
                'user_id' => $user->getId(),
1663
                'firstname' => $user->getFirstname(),
1664
                'lastname' => $user->getLastname(),
1665
                'email' => $user->getEmail(),
1666
                'username' => $user->getUsername(),
1667
            ];
1668
        }
1669
1670
        return $list;
1671
    }
1672
1673
    /**
1674
     * Subscribe user(s) to a specified group in current course (as a student).
1675
     *
1676
     * @param mixed  $userList  Can be an array with user-id's or a single user-id
1677
     * @param CGroup $group
1678
     * @param int    $course_id
1679
     *
1680
     * @return bool
1681
     */
1682
    public static function subscribeUsers($userList, CGroup $group = null, $course_id = null)
1683
    {
1684
        if (empty($group)) {
1685
            return false;
1686
        }
1687
        $userList = is_array($userList) ? $userList : [$userList];
1688
        $course_id = empty($course_id) ? api_get_course_int_id() : (int) $course_id;
1689
        $group_id = $group->getIid();
1690
1691
        if (!empty($userList)) {
1692
            $table = Database::get_course_table(TABLE_GROUP_USER);
1693
            foreach ($userList as $user_id) {
1694
                if (self::canUserSubscribe($user_id, $group)) {
1695
                    $user_id = (int) $user_id;
1696
                    $sql = "INSERT INTO $table (c_id, user_id, group_id, status, role)
1697
                            VALUES ('$course_id', '".$user_id."', '".$group_id."', 0, '')";
1698
                    Database::query($sql);
1699
                }
1700
            }
1701
        }
1702
1703
        return true;
1704
    }
1705
1706
    /**
1707
     * Subscribe tutor(s) to a specified group in current course.
1708
     *
1709
     * @param mixed $userList  Can be an array with user-id's or a single user-id
1710
     * @param array $groupInfo
1711
     * @param int   $course_id
1712
     */
1713
    public static function subscribeTutors($userList, CGroup $group = null, $course_id = 0)
1714
    {
1715
        if (empty($group)) {
1716
            return false;
1717
        }
1718
        $userList = is_array($userList) ? $userList : [$userList];
1719
        $result = true;
1720
        $course_id = isset($course_id) && !empty($course_id) ? intval($course_id) : api_get_course_int_id();
1721
        $table_group_tutor = Database::get_course_table(TABLE_GROUP_TUTOR);
1722
        $groupId = (int) $group->getIid();
1723
1724
        foreach ($userList as $user_id) {
1725
            $user_id = intval($user_id);
1726
            if (self::canUserSubscribe($user_id, $group, false)) {
1727
                $sql = 'INSERT INTO '.$table_group_tutor." (c_id, user_id, group_id)
1728
                        VALUES ('$course_id', '".$user_id."', '".$groupId."')";
1729
                $result = Database::query($sql);
1730
            }
1731
        }
1732
1733
        return $result;
1734
    }
1735
1736
    /**
1737
     * Unsubscribe user(s) from a specified group in current course.
1738
     *
1739
     * @param mixed $userList Can be an array with user-id's or a single user-id
1740
     *
1741
     * @return bool
1742
     */
1743
    public static function unsubscribeUsers($userList, CGroup $group = null)
1744
    {
1745
        if (empty($group)) {
1746
            return false;
1747
        }
1748
        $userList = is_array($userList) ? $userList : [$userList];
1749
        $table_group_user = Database::get_course_table(TABLE_GROUP_USER);
1750
        $group_id = $group->getIid();
1751
        $course_id = api_get_course_int_id();
1752
        $sql = 'DELETE FROM '.$table_group_user.'
1753
                WHERE
1754
                    group_id = '.$group_id.' AND
1755
                    user_id IN ('.implode(',', $userList).')
1756
                ';
1757
        Database::query($sql);
1758
    }
1759
1760
    /**
1761
     * Unsubscribe all users from one or more groups.
1762
     *
1763
     * @param int $groupId
1764
     *
1765
     * @return bool
1766
     */
1767
    public static function unsubscribeAllUsers($groupId)
1768
    {
1769
        $groupId = (int) $groupId;
1770
        if (empty($groupId)) {
1771
            return false;
1772
        }
1773
1774
        $table = Database::get_course_table(TABLE_GROUP_USER);
1775
        $sql = "DELETE FROM $table
1776
                WHERE
1777
                    group_id = $groupId ";
1778
1779
        return Database::query($sql);
1780
    }
1781
1782
    /**
1783
     * Unsubscribe all tutors from one or more groups.
1784
     *
1785
     * @param int $groupId iid
1786
     *
1787
     * @see unsubscribe_all_users. This function is almost an exact copy of that function.
1788
     *
1789
     * @return bool TRUE if successful
1790
     *
1791
     * @author Patrick Cool <[email protected]>, Ghent University
1792
     */
1793
    public static function unsubscribe_all_tutors($groupId)
1794
    {
1795
        $courseId = api_get_course_int_id();
1796
        $groupId = (int) $groupId;
1797
1798
        if (empty($courseId) || empty($groupId)) {
1799
            return false;
1800
        }
1801
1802
        if (!empty($groupId)) {
1803
            $table_group_tutor = Database::get_course_table(TABLE_GROUP_TUTOR);
1804
            $sql = "DELETE FROM $table_group_tutor
1805
                    WHERE group_id = $groupId ";
1806
            Database::query($sql);
1807
        }
1808
1809
        return true;
1810
    }
1811
1812
    /**
1813
     * Is the user a tutor of this group?
1814
     *
1815
     * @todo replace this function with $group->isUserTutor
1816
     */
1817
    public static function isTutorOfGroup($userId, CGroup $group = null)
1818
    {
1819
        if (empty($group)) {
1820
            return false;
1821
        }
1822
1823
        $userId = (int) $userId;
1824
        $group_id = (int) $group->getIid();
1825
1826
        $table = Database::get_course_table(TABLE_GROUP_TUTOR);
1827
1828
        $sql = "SELECT * FROM $table
1829
                WHERE
1830
                    user_id = $userId AND
1831
                    group_id = $group_id";
1832
        $result = Database::query($sql);
1833
1834
        return Database::num_rows($result) > 0;
1835
    }
1836
1837
    /**
1838
     * Is the user part of this group? This can be a tutor or a normal member
1839
     * you should use this function if the access to a tool or functionality is
1840
     * restricted to the people who are actually in the group
1841
     * before you had to check if the user was
1842
     * 1. a member of the group OR
1843
     * 2. a tutor of the group. This function combines both.
1844
     */
1845
    public static function isUserInGroup($user_id, CGroup $group)
1846
    {
1847
        $member = self::is_subscribed($user_id, $group);
1848
        if ($member) {
1849
            return true;
1850
        }
1851
1852
        $tutor = self::isTutorOfGroup($user_id, $group);
1853
        if ($tutor) {
1854
            return true;
1855
        }
1856
1857
        return false;
1858
    }
1859
1860
    /**
1861
     * Get all group's from a given course in which a given user is unsubscribed.
1862
     *
1863
     * @author  Patrick Cool
1864
     *
1865
     * @param int $course_id retrieve the groups for
1866
     * @param int $user_id   the ID of the user you want to know all its group memberships
1867
     *
1868
     * @return array
1869
     */
1870
    public static function get_group_ids($course_id, $user_id)
1871
    {
1872
        $groups = [];
1873
        $tbl_group = Database::get_course_table(TABLE_GROUP_USER);
1874
        $tbl_group_tutor = Database::get_course_table(TABLE_GROUP_TUTOR);
1875
        $user_id = intval($user_id);
1876
        $course_id = intval($course_id);
1877
1878
        $sql = "SELECT group_id FROM $tbl_group
1879
                WHERE user_id = '$user_id'";
1880
        $result = Database::query($sql);
1881
1882
        if ($result) {
1883
            while ($row = Database::fetch_array($result)) {
1884
                $groups[] = $row['group_id'];
1885
            }
1886
        }
1887
1888
        //Also loading if i'm the tutor
1889
        $sql = "SELECT group_id FROM $tbl_group_tutor
1890
                WHERE user_id = '$user_id'";
1891
        $result = Database::query($sql);
1892
        if ($result) {
1893
            while ($row = Database::fetch_array($result)) {
1894
                $groups[] = $row['group_id'];
1895
            }
1896
        }
1897
        if (!empty($groups)) {
1898
            array_filter($groups);
1899
        }
1900
1901
        return $groups;
1902
    }
1903
1904
    /**
1905
     * Check if a user has access to a certain group tool.
1906
     *
1907
     * @param int    $user_id The user id
1908
     * @param CGroup $group
1909
     * @param string $tool    The tool to check the access rights. This should be
1910
     *                        one of constants: GROUP_TOOL_DOCUMENTS
1911
     *
1912
     * @return bool true if the given user has access to the given tool in the
1913
     *              given course
1914
     */
1915
    public static function userHasAccess($user_id, CGroup $group = null, $tool)
1916
    {
1917
        if (null === $group) {
1918
            return false;
1919
        }
1920
1921
        // Admin have access everywhere
1922
        if (api_is_platform_admin()) {
1923
            return true;
1924
        }
1925
1926
        // Course admin also have access to everything
1927
        if (api_is_allowed_to_edit(false, true, true)) {
1928
            return true;
1929
        }
1930
1931
        if (0 == $group->getStatus()) {
1932
            return false;
1933
        }
1934
1935
        switch ($tool) {
1936
            case self::GROUP_TOOL_FORUM:
1937
                $toolStatus = $group->getForumState();
1938
                break;
1939
            case self::GROUP_TOOL_DOCUMENTS:
1940
                $toolStatus = $group->getDocState();
1941
                break;
1942
            case self::GROUP_TOOL_CALENDAR:
1943
                $toolStatus = $group->getCalendarState();
1944
                break;
1945
            case self::GROUP_TOOL_ANNOUNCEMENT:
1946
                $toolStatus = $group->getAnnouncementsState();
1947
                break;
1948
            case self::GROUP_TOOL_WORK:
1949
                $toolStatus = $group->getWorkState();
1950
                break;
1951
            case self::GROUP_TOOL_WIKI:
1952
                $toolStatus = $group->getWikiState();
1953
                break;
1954
            case self::GROUP_TOOL_CHAT:
1955
                $toolStatus = $group->getChatState();
1956
                break;
1957
            default:
1958
                return false;
1959
        }
1960
1961
        switch ($toolStatus) {
1962
            case self::TOOL_NOT_AVAILABLE:
1963
                return false;
1964
                break;
0 ignored issues
show
Unused Code introduced by
break is not strictly necessary here and could be removed.

The break statement is not necessary if it is preceded for example by a return statement:

switch ($x) {
    case 1:
        return 'foo';
        break; // This break is not necessary and can be left off.
}

If you would like to keep this construct to be consistent with other case statements, you can safely mark this issue as a false-positive.

Loading history...
1965
            case self::TOOL_PUBLIC:
1966
                return true;
1967
                break;
1968
            case self::TOOL_PRIVATE:
1969
                $userIsInGroup = self::isUserInGroup($user_id, $group);
1970
                if ($userIsInGroup) {
1971
                    return true;
1972
                }
1973
                break;
1974
            case self::TOOL_PRIVATE_BETWEEN_USERS:
1975
                // Only works for announcements for now
1976
                $userIsInGroup = self::isUserInGroup($user_id, $group);
1977
                if ($userIsInGroup && self::GROUP_TOOL_ANNOUNCEMENT == $tool) {
1978
                    return true;
1979
                }
1980
                break;
1981
        }
1982
1983
        return false;
1984
    }
1985
1986
    /**
1987
     * @param int $userId
1988
     * @param int $sessionId
1989
     *
1990
     * @return bool
1991
     */
1992
    public static function userHasAccessToBrowse($userId, CGroup $group = null, $sessionId = 0)
1993
    {
1994
        if (null === $group) {
1995
            return false;
1996
        }
1997
1998
        if (api_is_platform_admin()) {
1999
            return true;
2000
        }
2001
2002
        if (api_is_allowed_to_edit(false, true, true)) {
2003
            return true;
2004
        }
2005
2006
        if (!empty($sessionId)) {
2007
            if (api_is_coach($sessionId, api_get_course_int_id())) {
2008
                return true;
2009
            }
2010
2011
            if (api_is_drh()) {
2012
                if (SessionManager::isUserSubscribedAsHRM($sessionId, $userId)) {
2013
                    return true;
2014
                }
2015
            }
2016
        }
2017
2018
        if (self::isTutorOfGroup($userId, $group)) {
2019
            return true;
2020
        }
2021
2022
        if (0 == $group->getStatus()) {
2023
            return false;
2024
        }
2025
2026
        if (self::userHasAccess($userId, $group, self::GROUP_TOOL_FORUM) ||
2027
            self::userHasAccess($userId, $group, self::GROUP_TOOL_DOCUMENTS) ||
2028
            self::userHasAccess($userId, $group, self::GROUP_TOOL_CALENDAR) ||
2029
            self::userHasAccess($userId, $group, self::GROUP_TOOL_ANNOUNCEMENT) ||
2030
            self::userHasAccess($userId, $group, self::GROUP_TOOL_WORK) ||
2031
            self::userHasAccess($userId, $group, self::GROUP_TOOL_WIKI) ||
2032
            self::userHasAccess($userId, $group, self::GROUP_TOOL_CHAT)
2033
        ) {
2034
            return true;
2035
        }
2036
        //@todo check group session id
2037
        $groupSessionId = null;
2038
2039
        if (api_is_session_general_coach() && $groupSessionId == $sessionId) {
2040
            return true;
2041
        }
2042
2043
        return false;
2044
    }
2045
2046
    /**
2047
     * Get all groups where a specific user is subscribed.
2048
     *
2049
     * @param int $user_id
2050
     *
2051
     * @return array
2052
     */
2053
    public static function get_user_group_name($user_id)
2054
    {
2055
        $table_group_user = Database::get_course_table(TABLE_GROUP_USER);
2056
        $table_group = Database::get_course_table(TABLE_GROUP);
2057
        $user_id = intval($user_id);
2058
        $course_id = api_get_course_int_id();
2059
        $sql = "SELECT name
2060
                FROM $table_group g
2061
                INNER JOIN $table_group_user gu
2062
                ON (gu.group_id = g.iid)
2063
                WHERE
2064
                  gu.user_id = $user_id";
2065
        $res = Database::query($sql);
2066
        $groups = [];
2067
        while ($group = Database::fetch_array($res)) {
2068
            $groups[] .= $group['name'];
2069
        }
2070
2071
        return $groups;
2072
    }
2073
2074
    /**
2075
     * Get all groups where a specific user is subscribed.
2076
     *
2077
     * @param int      $user_id
2078
     * @param int      $courseId
2079
     * @param int|null $sessionId
2080
     *
2081
     * @return array
2082
     */
2083
    public static function getAllGroupPerUserSubscription($user_id, $courseId = 0, $sessionId = null)
2084
    {
2085
        $table_group_user = Database::get_course_table(TABLE_GROUP_USER);
2086
        $table_tutor_user = Database::get_course_table(TABLE_GROUP_TUTOR);
2087
        $table_group = Database::get_course_table(TABLE_GROUP);
2088
        $user_id = (int) $user_id;
2089
        $courseId = empty($courseId) ? api_get_course_int_id() : (int) $courseId;
2090
2091
        $sql = "SELECT DISTINCT g.*
2092
               FROM $table_group g
2093
               LEFT JOIN $table_group_user gu
2094
               ON (gu.group_id = g.iid)
2095
               LEFT JOIN $table_tutor_user tu
2096
               ON (tu.group_id = g.iid)
2097
               WHERE
2098
                  (gu.user_id = $user_id OR tu.user_id = $user_id) ";
2099
2100
        if (null !== $sessionId) {
2101
            $sessionId = (int) $sessionId;
2102
            $sql .= " AND g.session_id = $sessionId ";
2103
        }
2104
2105
        $res = Database::query($sql);
2106
        $groups = [];
2107
        while ($group = Database::fetch_array($res, 'ASSOC')) {
2108
            $groups[] = $group;
2109
        }
2110
2111
        return $groups;
2112
    }
2113
2114
    /**
2115
     * @param CGroup[] $groupList
2116
     * @param int      $category_id
2117
     *
2118
     * @return string
2119
     */
2120
    public static function processGroups($groupList, $category_id = 0)
2121
    {
2122
        $charset = 'UTF-8';
2123
        $category_id = (int) $category_id;
2124
        $totalRegistered = 0;
2125
        $group_data = [];
2126
        $user_info = api_get_user_info();
2127
        $session_id = api_get_session_id();
2128
        $user_id = $user_info['user_id'];
2129
        $hideGroup = api_get_setting('hide_course_group_if_no_tools_available');
2130
        $extraField = new ExtraField('survey');
2131
        $surveyGroupExists = $extraField->get_handler_field_info_by_field_variable('group_id') ? true : false;
2132
        $url = api_get_path(WEB_CODE_PATH).'group/';
2133
2134
        $confirmMessage = addslashes(
2135
            api_htmlentities(get_lang('Please confirm your choice'), ENT_QUOTES, $charset)
2136
        );
2137
2138
        foreach ($groupList as $group) {
2139
            $groupId = $group->getIid();
2140
2141
            // Validation when belongs to a session
2142
            $session_img = '';
2143
            //$session_img = api_get_session_image($group['session_id'], $user_info['status']);
2144
2145
            // All the tutors of this group
2146
            $tutors = $group->getTutors();
2147
            $isMember = self::is_subscribed($user_id, $group);
2148
2149
            // Create a new table-row
2150
            $row = [];
2151
            // Checkbox
2152
            if (api_is_allowed_to_edit(false, true) && count($groupList) > 1) {
2153
                $row[] = $groupId;
2154
            }
2155
2156
            if (self::userHasAccessToBrowse($user_id, $group, $session_id)) {
2157
                // Group name
2158
                $groupNameClass = null;
2159
                if (0 == $group->getStatus()) {
2160
                    $groupNameClass = 'muted';
2161
                }
2162
2163
                $group_name = '<a
2164
                    class="'.$groupNameClass.'"
2165
                    href="group_space.php?'.api_get_cidreq(true, false).'&gid='.$groupId.'">'.
2166
                    Security::remove_XSS($group->getName()).'</a> ';
2167
2168
                $group_name2 = '';
2169
                if (api_get_configuration_value('extra')) {
2170
                    $group_name2 = '<a
2171
                        href="group_space_tracking.php?'.api_get_cidreq(true, false).'&gid='.$groupId.'">'.
2172
                        get_lang('suivi_de').''.stripslashes($group->getName()).'</a>';
2173
                }
2174
2175
                /*
2176
                if (!empty($user_id) && !empty($this_group['id_tutor']) && $user_id == $this_group['id_tutor']) {
2177
                    $group_name .= Display::label(get_lang('my supervision'), 'success');
2178
                } elseif ($isMember) {
2179
                    $group_name .= Display::label(get_lang('my group'), 'success');
2180
                }*/
2181
2182
                /*if (api_is_allowed_to_edit() && !empty($this_group['session_name'])) {
2183
                    $group_name .= ' ('.$this_group['session_name'].')';
2184
                }
2185
                $group_name .= $session_img;*/
2186
2187
                $row[] = $group_name.$group_name2.'<br />'.stripslashes(trim($group->getDescription()));
2188
            } else {
2189
                if ('true' === $hideGroup) {
2190
                    continue;
2191
                }
2192
                $row[] = $group->getName().'<br />'.stripslashes(trim($group->getDescription()));
2193
            }
2194
2195
            // Tutor name
2196
            $tutor_info = '';
2197
            if (count($tutors) > 0) {
2198
                foreach ($tutors as $tutorGroup) {
2199
                    $tutor = $tutorGroup->getUser();
2200
                    $username = api_htmlentities(
2201
                        sprintf(get_lang('Login: %s'), $tutor->getUsername()),
2202
                        ENT_QUOTES
2203
                    );
2204
                    if ('true' === api_get_setting('show_email_addresses')) {
2205
                        $tutor_info .= Display::tag(
2206
                            'span',
2207
                            Display::encrypted_mailto_link(
2208
                                $tutor->getEmail(),
2209
                                UserManager::formatUserFullName($tutor)
2210
                            ),
2211
                            ['title' => $username]
2212
                        ).', ';
2213
                    } else {
2214
                        if (api_is_allowed_to_edit()) {
2215
                            $tutor_info .= Display::tag(
2216
                            'span',
2217
                                Display::encrypted_mailto_link(
2218
                                    $tutor->getEmail(),
2219
                                    UserManager::formatUserFullName($tutor)
2220
                                ),
2221
                                ['title' => $username]
2222
                            ).', ';
2223
                        } else {
2224
                            $tutor_info .= Display::tag(
2225
                                'span',
2226
                                    UserManager::formatUserFullName($tutor),
2227
                                ['title' => $username]
2228
                            ).', ';
2229
                        }
2230
                    }
2231
                }
2232
            }
2233
2234
            $tutor_info = api_substr(
2235
                $tutor_info,
2236
                0,
2237
                api_strlen($tutor_info) - 2
2238
            );
2239
            $row[] = $tutor_info;
2240
2241
            // Max number of members in group
2242
            $max_members = self::MEMBER_PER_GROUP_NO_LIMIT === $group->getMaxStudent() ? ' ' : ' / '.$group->getMaxStudent();
2243
            $registeredUsers = self::getStudentsCount($groupId);
2244
            // Number of members in group
2245
            $row[] = $registeredUsers.$max_members;
2246
2247
            // Self-registration / unregistration
2248
            if (!api_is_allowed_to_edit(false, true)) {
2249
                if (self::is_self_registration_allowed($user_id, $group)) {
2250
                    $row[] = '<a
2251
                        class = "btn btn-default"
2252
                        href="group.php?'.api_get_cidreq().'&category='.$category_id.'&action=self_reg&group_id='.$groupId.'"
2253
                        onclick="javascript:if(!confirm('."'".$confirmMessage."'".')) return false;">'.get_lang('register').'</a>';
2254
                } elseif (self::is_self_unregistration_allowed($user_id, $group)) {
2255
                    $row[] = '<a
2256
                        class = "btn btn-default"
2257
                        href="group.php?'.api_get_cidreq().'&category='.$category_id.'&action=self_unreg&group_id='.$groupId.'"
2258
                        onclick="javascript:if(!confirm('."'".$confirmMessage."'".')) return false;">'.get_lang('unregister').'</a>';
2259
                } else {
2260
                    $row[] = '-';
2261
                }
2262
            }
2263
2264
            // @todo fix group session access.
2265
            $groupSessionId = null;
2266
2267
            // Edit-links
2268
            if (api_is_allowed_to_edit(false, true) &&
2269
                !(api_is_session_general_coach() && $groupSessionId != $session_id)
2270
            ) {
2271
                $edit_actions = '<a
2272
                    href="'.$url.'settings.php?'.api_get_cidreq(true, false).'&gid='.$groupId.'"
2273
                    title="'.get_lang('Edit').'">'.
2274
                    Display::return_icon('edit.png', get_lang('Edit this group'), '', ICON_SIZE_SMALL).
2275
                    '</a>&nbsp;';
2276
2277
                if (1 == $group->getStatus()) {
2278
                    $edit_actions .= '<a
2279
                        href="'.api_get_self().'?'.api_get_cidreq(true, false).'&category='.$category_id.'&action=set_invisible&group_id='.$groupId.'"
2280
                        title="'.get_lang('Hide').'">'.
2281
                        Display::return_icon('visible.png', get_lang('Hide'), '', ICON_SIZE_SMALL).'</a>&nbsp;';
2282
                } else {
2283
                    $edit_actions .= '<a
2284
                        href="'.api_get_self().'?'.api_get_cidreq(true, false).'&category='.$category_id.'&action=set_visible&group_id='.$groupId.'"
2285
                        title="'.get_lang('Show').'">'.
2286
                        Display::return_icon('invisible.png', get_lang('Show'), '', ICON_SIZE_SMALL).'</a>&nbsp;';
2287
                }
2288
2289
                $edit_actions .= '<a
2290
                    href="'.$url.'member_settings.php?'.api_get_cidreq(true, false).'&gid='.$groupId.'"
2291
                    title="'.get_lang('Group members').'">'.
2292
                    Display::return_icon('user.png', get_lang('Group members'), '', ICON_SIZE_SMALL).'</a>&nbsp;';
2293
2294
                $edit_actions .= '<a
2295
                    href="'.$url.'group_overview.php?action=export&type=xls&'.api_get_cidreq(true, false).'&id='.$groupId.'"
2296
                    title="'.get_lang('Export users list').'">'.
2297
                    Display::return_icon('export_excel.png', get_lang('Export'), '', ICON_SIZE_SMALL).'</a>&nbsp;';
2298
2299
                if ($surveyGroupExists) {
2300
                    $edit_actions .= Display::url(
2301
                        Display::return_icon('survey.png', get_lang('ExportSurveyResults'), '', ICON_SIZE_SMALL),
2302
                        $url.'group_overview.php?action=export_surveys&'.api_get_cidreq(true, false).'&id='.$groupId
2303
                    ).'&nbsp;';
2304
                }
2305
                $edit_actions .= '<a
2306
                    href="'.api_get_self().'?'.api_get_cidreq(true, false).'&category='.$category_id.'&action=fill_one&group_id='.$groupId.'"
2307
                    onclick="javascript: if(!confirm('."'".$confirmMessage."'".')) return false;" title="'.get_lang('FillGroup').'">'.
2308
                    Display::return_icon('fill.png', get_lang('FillGroup'), '', ICON_SIZE_SMALL).'</a>&nbsp;';
2309
2310
                $edit_actions .= '<a
2311
                    href="'.api_get_self().'?'.api_get_cidreq(true, false).'&category='.$category_id.'&action=delete_one&group_id='.$groupId.'"
2312
                    onclick="javascript: if(!confirm('."'".$confirmMessage."'".')) return false;" title="'.get_lang('Delete').'">'.
2313
                    Display::return_icon('delete.png', get_lang('Delete'), '', ICON_SIZE_SMALL).'</a>&nbsp;';
2314
2315
                $row[] = $edit_actions;
2316
            }
2317
2318
            /*if (!empty($this_group['nbMember'])) {
2319
                $totalRegistered = $totalRegistered + $this_group['nbMember'];
2320
            }*/
2321
            $group_data[] = $row;
2322
        }
2323
2324
        // If no groups then don't show the table (only for students)
2325
        if (!api_is_allowed_to_edit(true, false)) {
2326
            if (empty($group_data)) {
2327
                return '';
2328
            }
2329
        }
2330
2331
        $table = new SortableTableFromArrayConfig(
2332
            $group_data,
2333
            1,
2334
            20,
2335
            'group_category_'.$category_id
2336
        );
2337
        $table->set_additional_parameters(['category' => $category_id]);
2338
        $column = 0;
2339
        if (api_is_allowed_to_edit(false, true) && count($groupList) > 1) {
2340
            $table->set_header($column++, '', false);
2341
        }
2342
        $table->set_header($column++, get_lang('Groups'));
2343
        $table->set_header($column++, get_lang('Group tutor'));
2344
        $table->set_header($column++, get_lang('Registered'), false);
2345
2346
        if (!api_is_allowed_to_edit(false, true)) {
2347
            // If self-registration allowed
2348
            $table->set_header($column++, get_lang('Registration'), false);
2349
        }
2350
2351
        if (api_is_allowed_to_edit(false, true)) {
2352
            // Only for course administrator
2353
            $table->set_header($column++, get_lang('Edit'), false);
2354
            $form_actions = [];
2355
            $form_actions['fill_selected'] = get_lang('Fill the group randomly with course students');
2356
            $form_actions['empty_selected'] = get_lang('unsubscribe all users');
2357
            $form_actions['delete_selected'] = get_lang('Delete');
2358
            if (count($groupList) > 1) {
2359
                $table->set_form_actions($form_actions, 'group');
2360
            }
2361
        }
2362
2363
        return $table->return_table();
2364
    }
2365
2366
    /**
2367
     * @param array $groupData
2368
     * @param bool  $deleteNotInArray
2369
     *
2370
     * @return array
2371
     */
2372
    public static function importCategoriesAndGroupsFromArray($groupData, $deleteNotInArray = false)
2373
    {
2374
        $result = [];
2375
        $elementsFound = [
2376
            'categories' => [],
2377
            'groups' => [],
2378
        ];
2379
2380
        $courseCode = api_get_course_id();
2381
        $sessionId = api_get_session_id();
2382
        $groupCategories = self::get_categories();
2383
2384
        if (empty($groupCategories)) {
2385
            $result['error'][] = get_lang('Create a category');
2386
2387
            return $result;
2388
        }
2389
2390
        foreach ($groupData as $data) {
2391
            $isCategory = empty($data['group']) ? true : false;
2392
            if ($isCategory) {
2393
                $categoryInfo = self::getCategoryByTitle($data['category']);
2394
                $categoryId = $categoryInfo['iid'];
2395
2396
                if (!empty($categoryInfo)) {
2397
                    // Update
2398
                    self::update_category(
2399
                        $categoryId,
2400
                        $data['category'],
2401
                        $data['description'],
2402
                        $data['doc_state'],
2403
                        $data['work_state'],
2404
                        $data['calendar_state'],
2405
                        $data['announcements_state'],
2406
                        $data['forum_state'],
2407
                        $data['wiki_state'],
2408
                        $data['chat_state'],
2409
                        $data['self_reg_allowed'],
2410
                        $data['self_unreg_allowed'],
2411
                        $data['max_student'],
2412
                        $data['groups_per_user'],
2413
                        $data['document_access']
2414
                    );
2415
                    $data['category_id'] = $categoryId;
2416
                    $result['updated']['category'][] = $data;
2417
                } else {
2418
                    // Add
2419
                    $categoryId = self::create_category(
2420
                        $data['category'],
2421
                        $data['description'],
2422
                        $data['doc_state'],
2423
                        $data['work_state'],
2424
                        $data['calendar_state'],
2425
                        $data['announcements_state'],
2426
                        $data['forum_state'],
2427
                        $data['wiki_state'],
2428
                        $data['chat_state'],
2429
                        $data['self_reg_allowed'],
2430
                        $data['self_unreg_allowed'],
2431
                        $data['max_student'],
2432
                        $data['groups_per_user']
2433
                    );
2434
2435
                    if ($categoryId) {
2436
                        $data['category_id'] = $categoryId;
2437
                        $result['added']['category'][] = $data;
2438
                    }
2439
                }
2440
                $elementsFound['categories'][] = $categoryId;
2441
            } else {
2442
                $groupInfo = self::getGroupByName($data['group']);
2443
                $categoryInfo = [];
2444
                if (isset($data['category'])) {
2445
                    $categoryInfo = self::getCategoryByTitle($data['category']);
2446
                }
2447
                $categoryId = null;
2448
                if (!empty($categoryInfo)) {
2449
                    $categoryId = $categoryInfo['iid'];
2450
                } else {
2451
                    if (!empty($groupCategories) && isset($groupCategories[0])) {
2452
                        $defaultGroupCategory = $groupCategories[0];
2453
                        $categoryId = $defaultGroupCategory['iid'];
2454
                    }
2455
                }
2456
2457
                if (empty($groupInfo)) {
2458
                    // Add
2459
                    $groupId = self::create_group(
2460
                        $data['group'],
2461
                        $categoryId,
2462
                        null,
2463
                        $data['max_student']
2464
                    );
2465
2466
                    if ($groupId) {
2467
                        self::set_group_properties(
2468
                            $groupId,
2469
                            $data['group'],
2470
                            $data['description'],
2471
                            $data['max_student'],
2472
                            $data['doc_state'],
2473
                            $data['work_state'],
2474
                            $data['calendar_state'],
2475
                            $data['announcements_state'],
2476
                            $data['forum_state'],
2477
                            $data['wiki_state'],
2478
                            $data['chat_state'],
2479
                            $data['self_reg_allowed'],
2480
                            $data['self_unreg_allowed'],
2481
                            $categoryId
2482
                        );
2483
                        $data['group_id'] = $groupId;
2484
                        $result['added']['group'][] = $data;
2485
                    }
2486
                    $groupInfo = self::get_group_properties($groupId, true);
2487
                } else {
2488
                    // Update
2489
                    $groupId = $groupInfo['iid'];
2490
                    self::set_group_properties(
2491
                        $groupId,
2492
                        $data['group'],
2493
                        $data['description'],
2494
                        $data['max_student'],
2495
                        $data['doc_state'],
2496
                        $data['work_state'],
2497
                        $data['calendar_state'],
2498
                        $data['announcements_state'],
2499
                        $data['forum_state'],
2500
                        $data['wiki_state'],
2501
                        $data['chat_state'],
2502
                        $data['self_reg_allowed'],
2503
                        $data['self_unreg_allowed'],
2504
                        $categoryId
2505
                    );
2506
2507
                    $data['group_id'] = $groupId;
2508
                    $result['updated']['group'][] = $data;
2509
                    $groupInfo = self::get_group_properties($groupId);
2510
                }
2511
2512
                $students = isset($data['students']) ? explode(',', $data['students']) : [];
2513
                if (!empty($students)) {
2514
                    $studentUserIdList = [];
2515
                    foreach ($students as $student) {
2516
                        $userInfo = api_get_user_info_from_username($student);
2517
2518
                        if (!$userInfo) {
2519
                            continue;
2520
                        }
2521
2522
                        if (!CourseManager::is_user_subscribed_in_course(
2523
                                $userInfo['user_id'],
2524
                                $courseCode,
2525
                                !empty($sessionId),
2526
                                $sessionId
2527
                            )
2528
                        ) {
2529
                            Display::addFlash(
2530
                                Display::return_message(
2531
                                    sprintf(
2532
                                        get_lang('Student %s is no subscribed to this course'),
2533
                                        $userInfo['complete_name']
2534
                                    ),
2535
                                    'warning'
2536
                                )
2537
                            );
2538
                            continue;
2539
                        }
2540
2541
                        $studentUserIdList[] = $userInfo['user_id'];
2542
                    }
2543
                    self::subscribeUsers($studentUserIdList, api_get_group_entity($groupInfo['iid']));
2544
                }
2545
2546
                $tutors = isset($data['tutors']) ? explode(',', $data['tutors']) : [];
2547
                if (!empty($tutors)) {
2548
                    $tutorIdList = [];
2549
                    foreach ($tutors as $tutor) {
2550
                        $userInfo = api_get_user_info_from_username($tutor);
2551
2552
                        if (!$userInfo) {
2553
                            continue;
2554
                        }
2555
2556
                        if (!CourseManager::is_user_subscribed_in_course(
2557
                                $userInfo['user_id'],
2558
                                $courseCode,
2559
                                !empty($sessionId),
2560
                                $sessionId
2561
                            )
2562
                        ) {
2563
                            Display::addFlash(
2564
                                Display::return_message(
2565
                                    sprintf(get_lang('Tutor %s is no subscribed to this course'), $userInfo['complete_name']),
2566
                                    'warning'
2567
                                )
2568
                            );
2569
2570
                            continue;
2571
                        }
2572
2573
                        $tutorIdList[] = $userInfo['user_id'];
2574
                    }
2575
                    self::subscribeTutors($tutorIdList, api_get_group_entity($groupInfo['iid']));
2576
                }
2577
2578
                $elementsFound['groups'][] = $groupId;
2579
            }
2580
        }
2581
2582
        if ($deleteNotInArray) {
2583
            // Check categories
2584
            $categories = self::get_categories();
2585
            foreach ($categories as $category) {
2586
                if (!in_array($category['iid'], $elementsFound['categories'])) {
2587
                    self::delete_category($category['iid']);
2588
                    $category['category'] = $category['title'];
2589
                    $result['deleted']['category'][] = $category;
2590
                }
2591
            }
2592
2593
            $groups = self::get_groups();
2594
            foreach ($groups as $group) {
2595
                if (!in_array($group->getIid(), $elementsFound['groups'])) {
2596
                    self::deleteGroup($group);
2597
                    $result['deleted']['group'][] = $group;
2598
                }
2599
            }
2600
        }
2601
2602
        return $result;
2603
    }
2604
2605
    /**
2606
     * Export all categories/group from a course to an array.
2607
     * This function works only in a context of a course.
2608
     *
2609
     * @param int  $groupId
2610
     * @param bool $loadUsers
2611
     *
2612
     * @return array
2613
     */
2614
    public static function exportCategoriesAndGroupsToArray($groupId = null, $loadUsers = false)
2615
    {
2616
        $data = [];
2617
        $data[] = [
2618
            'category',
2619
            'group',
2620
            'description',
2621
            'announcements_state',
2622
            'calendar_state',
2623
            'chat_state',
2624
            'doc_state',
2625
            'forum_state',
2626
            'work_state',
2627
            'wiki_state',
2628
            'max_student',
2629
            'self_reg_allowed',
2630
            'self_unreg_allowed',
2631
            'groups_per_user',
2632
        ];
2633
2634
        $count = 1;
2635
2636
        if ($loadUsers) {
2637
            $data[0][] = 'students';
2638
            $data[0][] = 'tutors';
2639
        }
2640
2641
        if (false == $loadUsers) {
2642
            $categories = self::get_categories();
2643
2644
            foreach ($categories as $categoryInfo) {
2645
                $data[$count] = [
2646
                    $categoryInfo['title'],
2647
                    null,
2648
                    $categoryInfo['description'],
2649
                    $categoryInfo['announcements_state'],
2650
                    $categoryInfo['calendar_state'],
2651
                    $categoryInfo['chat_state'],
2652
                    $categoryInfo['doc_state'],
2653
                    $categoryInfo['forum_state'],
2654
                    $categoryInfo['work_state'],
2655
                    $categoryInfo['wiki_state'],
2656
                    $categoryInfo['max_student'],
2657
                    $categoryInfo['self_reg_allowed'],
2658
                    $categoryInfo['self_unreg_allowed'],
2659
                    $categoryInfo['groups_per_user'],
2660
                ];
2661
                $count++;
2662
            }
2663
        }
2664
2665
        $groups = self::get_group_list();
2666
        foreach ($groups as $groupInfo) {
2667
            $groupId = $groupInfo['iid'];
2668
            $categoryTitle = null;
2669
            $categoryInfo = [];
2670
            if (isset($groupInfo['category'])) {
2671
                $categoryInfo = self::get_category($groupInfo['category']);
2672
            }
2673
2674
            $groupSettings = self::get_group_properties($groupId);
2675
            if (!empty($categoryInfo)) {
2676
                $categoryTitle = $categoryInfo['title'];
2677
            }
2678
2679
            $users = self::getStudents($groupId);
2680
            $userList = [];
2681
            foreach ($users as $user) {
2682
                $user = api_get_user_info($user['user_id']);
2683
                $userList[] = $user['username'];
2684
            }
2685
2686
            $tutors = self::getTutors($groupInfo);
2687
            $tutorList = [];
2688
            foreach ($tutors as $user) {
2689
                $user = api_get_user_info($user['user_id']);
2690
                $tutorList[] = $user['username'];
2691
            }
2692
2693
            $userListToString = null;
2694
            if (!empty($userList)) {
2695
                $userListToString = implode(',', $userList);
2696
            }
2697
2698
            $tutorListToString = null;
2699
            if (!empty($tutorList)) {
2700
                $tutorListToString = implode(',', $tutorList);
2701
            }
2702
2703
            $data[$count] = [
2704
                $categoryTitle,
2705
                $groupSettings['name'],
2706
                $groupSettings['description'],
2707
                $groupSettings['announcements_state'],
2708
                $groupSettings['calendar_state'],
2709
                $groupSettings['chat_state'],
2710
                $groupSettings['doc_state'],
2711
                $groupSettings['forum_state'],
2712
                $groupSettings['work_state'],
2713
                $groupSettings['wiki_state'],
2714
                $groupSettings['maximum_number_of_students'],
2715
                $groupSettings['self_registration_allowed'],
2716
                $groupSettings['self_unregistration_allowed'],
2717
                null,
2718
            ];
2719
2720
            if ($loadUsers) {
2721
                $data[$count][] = $userListToString;
2722
                $data[$count][] = $tutorListToString;
2723
            }
2724
2725
            if (!empty($groupId)) {
2726
                if ($groupId == $groupInfo['iid']) {
2727
                    break;
2728
                }
2729
            }
2730
            $count++;
2731
        }
2732
2733
        return $data;
2734
    }
2735
2736
    /**
2737
     * @param string $default
2738
     */
2739
    public static function getSettingBar($default)
2740
    {
2741
        $activeSettings = null;
2742
        $activeTutor = null;
2743
        $activeMember = null;
2744
2745
        switch ($default) {
2746
            case 'settings':
2747
                $activeSettings = 'active';
2748
                break;
2749
            case 'tutor':
2750
                $activeTutor = 'active';
2751
                break;
2752
            case 'member':
2753
                $activeMember = 'active';
2754
                break;
2755
        }
2756
2757
        $url = api_get_path(WEB_CODE_PATH).'group/%s?'.api_get_cidreq();
2758
2759
        echo '
2760
            <ul class="nav nav-tabs">
2761
                <li class="nav-item">
2762
                    <a class="nav-link '.$activeSettings.'"
2763
                        id="group_settings_tab" href="'.sprintf($url, 'settings.php').'">
2764
                    '.Display::return_icon('settings.png').' '.get_lang('Settings').'
2765
                    </a>
2766
                </li>
2767
                <li class="nav-item">
2768
                    <a class="nav-link '.$activeMember.'"
2769
                        id="group_members_tab" href="'.sprintf($url, 'member_settings.php').'">
2770
                    '.Display::return_icon('user.png').' '.get_lang('Group members').'</a>
2771
                </li>
2772
                <li class="nav-item">
2773
                    <a class="nav-link  '.$activeTutor.'"
2774
                        id="group_tutors_tab" href="'.sprintf($url, 'tutor_settings.php').'">
2775
                    '.Display::return_icon('teacher.png').' '.get_lang('Group tutors').'
2776
                    </a>
2777
                </li>
2778
            </ul>';
2779
    }
2780
2781
    public static function groupOverview($group, $url)
2782
    {
2783
        $groupId = $group['iid'];
2784
        $content = '<li>';
2785
        $content .= Display::tag(
2786
            'h3',
2787
            Display::url(
2788
                Security::remove_XSS($group['name']),
2789
                $url.'&gid='.$groupId
2790
            )
2791
        );
2792
        $users = self::getTutors($group);
2793
        if (!empty($users)) {
2794
            $content .= '<ul>';
2795
            $content .= "<li>".Display::tag('h4', get_lang('Tutors'))."</li><ul>";
2796
            foreach ($users as $user) {
2797
                $userInfo = api_get_user_info($user['user_id']);
2798
                $content .= '<li title="'.$userInfo['username'].'">'.
2799
                    $userInfo['complete_name_with_username'].
2800
                    '</li>';
2801
            }
2802
            $content .= '</ul>';
2803
            $content .= '</ul>';
2804
        }
2805
2806
        $users = self::getStudents($group['iid']);
2807
        if (!empty($users)) {
2808
            $content .= '<ul>';
2809
            $content .= "<li>".Display::tag('h4', get_lang('Students'))."</li><ul>";
2810
            foreach ($users as $user) {
2811
                $userInfo = api_get_user_info($user['user_id']);
2812
                $content .= '<li title="'.$userInfo['username'].'">'.
2813
                    $userInfo['complete_name_with_username'].
2814
                    '</li>';
2815
            }
2816
            $content .= '</ul>';
2817
            $content .= '</ul>';
2818
        }
2819
        $content .= '</li>';
2820
2821
        return $content;
2822
    }
2823
2824
    /**
2825
     * @param Course $course
2826
     * @param string $keyword
2827
     *
2828
     * @return string
2829
     */
2830
    public static function getOverview(Course $course, $keyword = '')
2831
    {
2832
        $content = null;
2833
        $categories = self::get_categories();
2834
        $url = api_get_path(WEB_CODE_PATH).'group/group_space.php?'.api_get_cidreq(true, false);
2835
        if (!empty($categories)) {
2836
            foreach ($categories as $category) {
2837
                if ('true' === api_get_setting('allow_group_categories')) {
2838
                    $content .= '<h2>'.$category['title'].'</h2>';
2839
                }
2840
                $groups = self::get_group_list($category['iid'], $course, null, 0, false, $keyword);
2841
                $content .= '<ul>';
2842
                if (!empty($groups)) {
2843
                    foreach ($groups as $group) {
2844
                        $content .= self::groupOverview($group, $url);
2845
                    }
2846
                }
2847
                $content .= '</ul>';
2848
            }
2849
        }
2850
2851
        // Check groups with no categories.
2852
        $groups = self::get_group_list(null, $course, null, api_get_session_id(), false, true);
2853
        if (!empty($groups)) {
2854
            $content .= '<h2>'.get_lang('NoCategorySelected').'</h2>';
2855
            $content .= '<ul>';
2856
            foreach ($groups as $group) {
2857
                if (!empty($group['category_id'])) {
2858
                    continue;
2859
                }
2860
                $content .= self::groupOverview($group, $url);
2861
            }
2862
            $content .= '</ul>';
2863
        }
2864
2865
        return $content;
2866
    }
2867
2868
    /**
2869
     * Returns the search form.
2870
     *
2871
     * @return string
2872
     */
2873
    public static function getSearchForm()
2874
    {
2875
        $url = api_get_path(WEB_CODE_PATH).'group/group_overview.php?'.api_get_cidreq();
2876
        $form = new FormValidator(
2877
            'search_groups',
2878
            'get',
2879
            $url,
2880
            null,
2881
            ['class' => 'form-search'],
2882
            FormValidator::LAYOUT_INLINE
2883
        );
2884
        $form->addElement('text', 'keyword');
2885
        $form->addCourseHiddenParams();
2886
        $form->addButtonSearch();
2887
2888
        return $form->toHtml();
2889
    }
2890
2891
    public static function setStatus(CGroup $group, $status)
2892
    {
2893
        $group->setStatus($status);
2894
        $em = Database::getManager();
2895
        $em->persist($group);
2896
        $em->flush();
2897
    }
2898
2899
    public static function setVisible(CGroup $group)
2900
    {
2901
        self::setStatus($group, true);
2902
    }
2903
2904
    public static function setInvisible(CGroup $group)
2905
    {
2906
        self::setStatus($group, false);
2907
    }
2908
2909
    /**
2910
     * @param int   $userId
2911
     * @param int   $courseId
2912
     * @param array $documentInfoToBeCheck
2913
     * @param bool  $blockPage
2914
     *
2915
     * @return bool
2916
     */
2917
    public static function allowUploadEditDocument(
2918
        $userId,
2919
        $courseId,
2920
        CGroup $group,
2921
        $documentInfoToBeCheck = null,
2922
        $blockPage = false
2923
    ) {
2924
        // Admin and teachers can make any change no matter what
2925
        if (api_is_platform_admin() || api_is_allowed_to_edit(false, true)) {
2926
            return true;
2927
        }
2928
2929
        if (empty($group)) {
2930
            if ($blockPage) {
2931
                api_not_allowed(true);
2932
            }
2933
2934
            return false;
2935
        }
2936
2937
        // Tutor can also make any change
2938
        $isTutor = self::isTutorOfGroup($userId, $group);
2939
2940
        if ($isTutor) {
2941
            return true;
2942
        }
2943
2944
        // Just in case also check if document in group is available
2945
        if (0 == $group->getDocState()) {
2946
            if ($blockPage) {
2947
                api_not_allowed(true);
2948
            }
2949
2950
            return false;
2951
        }
2952
2953
        // Default behaviour
2954
        $documentAccess = self::DOCUMENT_MODE_SHARE;
2955
2956
        // Check category document access
2957
        /*$allowCategoryGroupDocumentAccess = api_get_configuration_value('group_category_document_access');
2958
        if ($allowCategoryGroupDocumentAccess) {
2959
            $category = GroupManager::get_category_from_group($groupInfo['iid']);
2960
            if (!empty($category) && isset($category['document_access'])) {
2961
                $documentAccess = (int) $category['document_access'];
2962
            }
2963
        }*/
2964
2965
        // Check group document access
2966
        $allow = api_get_configuration_value('group_document_access');
2967
        if ($allow) {
2968
            $documentAccess = $group->getDocumentAccess();
2969
        }
2970
2971
        // Check access for students
2972
        $result = false;
2973
        switch ($documentAccess) {
2974
            case self::DOCUMENT_MODE_SHARE:
2975
                // Default chamilo behaviour
2976
                // Student can upload his own content, cannot modify another content.
2977
                $isMember = self::is_subscribed($userId, $group);
2978
                if ($isMember) {
2979
                    // No document to check, allow access to document feature.
2980
                    if (empty($documentInfoToBeCheck)) {
2981
                        $result = true;
2982
                    } else {
2983
                        // Member can only edit his own document
2984
                        $authorId = isset($documentInfoToBeCheck['insert_user_id']) ? $documentInfoToBeCheck['insert_user_id'] : 0;
2985
                        // If "insert_user_id" is not set, check the author id from c_item_property
2986
                        if (empty($authorId) && isset($documentInfoToBeCheck['id'])) {
2987
                            // @todo use resources
2988
                            /*$documentInfo = api_get_item_property_info(
2989
                                $courseId,
2990
                                'document',
2991
                                $documentInfoToBeCheck['id'],
2992
                                0
2993
                            );
2994
                            // Try to find this document in the session
2995
                            if (!empty($sessionId)) {
2996
                                $documentInfo = api_get_item_property_info(
2997
                                    $courseId,
2998
                                    'document',
2999
                                    $documentInfoToBeCheck['id'],
3000
                                    api_get_session_id()
3001
                                );
3002
                            }
3003
3004
                            if (!empty($documentInfo) && isset($documentInfo['insert_user_id'])) {
3005
                                $authorId = $documentInfo['insert_user_id'];
3006
                            }*/
3007
                        }
3008
3009
                        if ($authorId == $userId) {
3010
                            $result = true;
3011
                        }
3012
                    }
3013
                }
3014
                break;
3015
            case self::DOCUMENT_MODE_READ_ONLY:
3016
                // Student cannot upload content, cannot modify another content.
3017
                $result = false;
3018
                break;
3019
            case self::DOCUMENT_MODE_COLLABORATION:
3020
                // Student can upload content, can modify another content.
3021
                $isMember = self::is_subscribed($userId, $group);
3022
                if ($isMember) {
3023
                    $result = true;
3024
                }
3025
                break;
3026
        }
3027
3028
        if ($blockPage && false == $result) {
3029
            api_not_allowed(true);
3030
        }
3031
3032
        return $result;
3033
    }
3034
}
3035