Passed
Pull Request — 1.11.x (#4109)
by Angel Fernando Quiroz
09:46
created

Agenda::addEvent()   F

Complexity

Conditions 25
Paths 1236

Size

Total Lines 224
Code Lines 150

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 1
Metric Value
eloc 150
c 1
b 0
f 1
dl 0
loc 224
rs 0
cc 25
nop 15
nc 1236

How to fix   Long Method    Complexity    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\AgendaEventInvitation;
6
use Chamilo\CoreBundle\Entity\AgendaEventInvitee;
7
use Chamilo\CoreBundle\Entity\AgendaReminder;
8
use Chamilo\UserBundle\Entity\User;
9
10
/**
11
 * Class Agenda.
12
 *
13
 * @author: Julio Montoya <[email protected]>
14
 */
15
class Agenda
16
{
17
    public $events = [];
18
    /** @var string Current type */
19
    public $type = 'personal';
20
    public $types = ['personal', 'admin', 'course'];
21
    public $sessionId = 0;
22
    public $senderId;
23
    /** @var array */
24
    public $course;
25
    /** @var string */
26
    public $comment;
27
    public $eventStudentPublicationColor;
28
    /** @var array */
29
    private $sessionInfo;
30
    /** @var bool */
31
    private $isAllowedToEdit;
32
33
    /**
34
     * Constructor.
35
     *
36
     * @param string $type
37
     * @param int    $senderId  Optional The user sender ID
38
     * @param int    $courseId  Optional. The course ID
39
     * @param int    $sessionId Optional The session ID
40
     */
41
    public function __construct(
42
        $type,
43
        $senderId = 0,
44
        $courseId = 0,
45
        $sessionId = 0
46
    ) {
47
        // Table definitions
48
        $this->tbl_global_agenda = Database::get_main_table(TABLE_MAIN_SYSTEM_CALENDAR);
49
        $this->tbl_personal_agenda = Database::get_main_table(TABLE_PERSONAL_AGENDA);
50
        $this->tbl_course_agenda = Database::get_course_table(TABLE_AGENDA);
51
        $this->table_repeat = Database::get_course_table(TABLE_AGENDA_REPEAT);
52
53
        $this->setType($type);
54
        $this->setSenderId($senderId ?: api_get_user_id());
55
        $isAllowToEdit = false;
56
57
        switch ($type) {
58
            case 'course':
59
                $sessionId = $sessionId ?: api_get_session_id();
60
                $sessionInfo = api_get_session_info($sessionId);
61
                $this->setSessionId($sessionId);
62
                $this->setSessionInfo($sessionInfo);
63
64
                // Setting the course object if we are in a course
65
                $courseInfo = api_get_course_info_by_id($courseId);
66
                if (!empty($courseInfo)) {
67
                    $this->set_course($courseInfo);
68
                }
69
70
                // Check if teacher/admin rights.
71
                $isAllowToEdit = api_is_allowed_to_edit(false, true);
72
                // Check course setting.
73
                if (api_get_course_setting('allow_user_edit_agenda') == '1'
74
                    && api_is_allowed_in_course()
75
                ) {
76
                    $isAllowToEdit = true;
77
                }
78
79
                $groupId = api_get_group_id();
80
                if (!empty($groupId)) {
81
                    $groupInfo = GroupManager::get_group_properties($groupId);
82
                    $userHasAccess = GroupManager::user_has_access(
83
                        api_get_user_id(),
84
                        $groupInfo['iid'],
85
                        GroupManager::GROUP_TOOL_CALENDAR
86
                    );
87
                    $isTutor = GroupManager::is_tutor_of_group(
88
                        api_get_user_id(),
89
                        $groupInfo
90
                    );
91
92
                    $isGroupAccess = $userHasAccess || $isTutor;
93
                    $isAllowToEdit = false;
94
                    if ($isGroupAccess) {
95
                        $isAllowToEdit = true;
96
                    }
97
                }
98
99
                if (false === $isAllowToEdit && !empty($sessionId)) {
100
                    $allowDhrToEdit = api_get_configuration_value('allow_agenda_edit_for_hrm');
101
                    if ($allowDhrToEdit) {
102
                        $isHrm = SessionManager::isUserSubscribedAsHRM($sessionId, api_get_user_id());
103
                        if ($isHrm) {
104
                            $isAllowToEdit = true;
105
                        }
106
                    }
107
                }
108
                break;
109
            case 'admin':
110
                $isAllowToEdit = api_is_platform_admin();
111
                break;
112
            case 'personal':
113
                $isAllowToEdit = !api_is_anonymous();
114
                break;
115
        }
116
117
        $this->setIsAllowedToEdit($isAllowToEdit);
118
        $this->events = [];
119
        $agendaColors = array_merge(
120
            [
121
                'platform' => 'red', //red
122
                'course' => '#458B00', //green
123
                'group' => '#A0522D', //siena
124
                'session' => '#00496D', // kind of green
125
                'other_session' => '#999', // kind of green
126
                'personal' => 'steel blue', //steel blue
127
                'student_publication' => '#FF8C00', //DarkOrange
128
            ],
129
            api_get_configuration_value('agenda_colors') ?: []
130
        );
131
132
        // Event colors
133
        $this->event_platform_color = $agendaColors['platform'];
134
        $this->event_course_color = $agendaColors['course'];
135
        $this->event_group_color = $agendaColors['group'];
136
        $this->event_session_color = $agendaColors['session'];
137
        $this->eventOtherSessionColor = $agendaColors['other_session'];
138
        $this->event_personal_color = $agendaColors['personal'];
139
        $this->eventStudentPublicationColor = $agendaColors['student_publication'];
140
    }
141
142
    /**
143
     * @param int $senderId
144
     */
145
    public function setSenderId($senderId)
146
    {
147
        $this->senderId = (int) $senderId;
148
    }
149
150
    /**
151
     * @return int
152
     */
153
    public function getSenderId()
154
    {
155
        return $this->senderId;
156
    }
157
158
    /**
159
     * @param string $type can be 'personal', 'admin'  or  'course'
160
     */
161
    public function setType($type)
162
    {
163
        $type = (string) trim($type);
164
        $typeList = $this->getTypes();
165
        if (in_array($type, $typeList, true)) {
166
            $this->type = $type;
167
        }
168
    }
169
170
    /**
171
     * Returns the type previously set (and filtered) through setType
172
     * If setType() was not called, then type defaults to "personal" as
173
     * set in the class definition.
174
     */
175
    public function getType()
176
    {
177
        if (isset($this->type)) {
178
            return $this->type;
179
        }
180
    }
181
182
    /**
183
     * @param int $id
184
     */
185
    public function setSessionId($id)
186
    {
187
        $this->sessionId = (int) $id;
188
    }
189
190
    /**
191
     * @param array $sessionInfo
192
     */
193
    public function setSessionInfo($sessionInfo)
194
    {
195
        $this->sessionInfo = $sessionInfo;
196
    }
197
198
    /**
199
     * @return int $id
200
     */
201
    public function getSessionId()
202
    {
203
        return $this->sessionId;
204
    }
205
206
    /**
207
     * @param array $courseInfo
208
     */
209
    public function set_course($courseInfo)
210
    {
211
        $this->course = $courseInfo;
212
    }
213
214
    /**
215
     * @return array
216
     */
217
    public function getTypes()
218
    {
219
        return $this->types;
220
    }
221
222
    /**
223
     * Adds an event to the calendar.
224
     *
225
     * @param string $start                 datetime format: 2012-06-14 09:00:00 in local time
226
     * @param string $end                   datetime format: 2012-06-14 09:00:00 in local time
227
     * @param string $allDay                (true, false)
228
     * @param string $title
229
     * @param string $content
230
     * @param array  $usersToSend           array('everyone') or a list of user/group ids
231
     * @param bool   $addAsAnnouncement     event as a *course* announcement
232
     * @param int    $parentEventId
233
     * @param array  $attachmentArray       array of $_FILES['']
234
     * @param array  $attachmentCommentList
235
     * @param string $eventComment
236
     * @param string $color
237
     *
238
     * @return int
239
     */
240
    public function addEvent(
241
        $start,
242
        $end,
243
        $allDay,
244
        $title,
245
        $content,
246
        $usersToSend = [],
247
        $addAsAnnouncement = false,
248
        $parentEventId = null,
249
        $attachmentArray = [],
250
        $attachmentCommentList = [],
251
        $eventComment = null,
252
        $color = '',
253
        array $inviteesList = [],
254
        bool $isCollective = false,
255
        array $reminders = []
256
    ) {
257
        $start = api_get_utc_datetime($start);
258
        $end = api_get_utc_datetime($end);
259
        $allDay = isset($allDay) && ($allDay === 'true' || $allDay == 1) ? 1 : 0;
260
        $id = null;
261
262
        switch ($this->type) {
263
            case 'personal':
264
                $attributes = [
265
                    'user' => api_get_user_id(),
266
                    'title' => $title,
267
                    'text' => $content,
268
                    'date' => $start,
269
                    'enddate' => $end,
270
                    'all_day' => $allDay,
271
                    'color' => $color,
272
                ];
273
274
                $id = Database::insert(
275
                    $this->tbl_personal_agenda,
276
                    $attributes
277
                );
278
279
                if (api_get_configuration_value('agenda_collective_invitations')) {
280
                    Agenda::saveCollectiveProperties($inviteesList, $isCollective, $id);
281
                }
282
                break;
283
            case 'course':
284
                $attributes = [
285
                    'title' => $title,
286
                    'content' => $content,
287
                    'start_date' => $start,
288
                    'end_date' => $end,
289
                    'all_day' => $allDay,
290
                    'session_id' => $this->getSessionId(),
291
                    'c_id' => $this->course['real_id'],
292
                    'comment' => $eventComment,
293
                    'color' => $color,
294
                ];
295
296
                if (!empty($parentEventId)) {
297
                    $attributes['parent_event_id'] = $parentEventId;
298
                }
299
300
                $senderId = $this->getSenderId();
301
                $sessionId = $this->getSessionId();
302
303
                // Simple course event.
304
                $id = Database::insert($this->tbl_course_agenda, $attributes);
305
306
                if ($id) {
307
                    $sql = "UPDATE ".$this->tbl_course_agenda." SET id = iid WHERE iid = $id";
308
                    Database::query($sql);
309
310
                    $groupId = api_get_group_id();
311
                    $groupInfo = [];
312
                    if ($groupId) {
313
                        $groupInfo = GroupManager::get_group_properties(
314
                            $groupId
315
                        );
316
                    }
317
318
                    if (!empty($usersToSend)) {
319
                        $sendTo = $this->parseSendToArray($usersToSend);
320
                        if ($sendTo['everyone']) {
321
                            api_item_property_update(
322
                                $this->course,
323
                                TOOL_CALENDAR_EVENT,
324
                                $id,
325
                                'AgendaAdded',
326
                                $senderId,
327
                                $groupInfo,
328
                                '',
329
                                $start,
330
                                $end,
331
                                $sessionId
332
                            );
333
                            api_item_property_update(
334
                                $this->course,
335
                                TOOL_CALENDAR_EVENT,
336
                                $id,
337
                                'visible',
338
                                $senderId,
339
                                $groupInfo,
340
                                '',
341
                                $start,
342
                                $end,
343
                                $sessionId
344
                            );
345
                        } else {
346
                            // Storing the selected groups
347
                            if (!empty($sendTo['groups'])) {
348
                                foreach ($sendTo['groups'] as $group) {
349
                                    $groupInfoItem = [];
350
                                    if ($group) {
351
                                        $groupInfoItem = GroupManager::get_group_properties($group);
352
                                    }
353
354
                                    api_item_property_update(
355
                                        $this->course,
356
                                        TOOL_CALENDAR_EVENT,
357
                                        $id,
358
                                        'AgendaAdded',
359
                                        $senderId,
360
                                        $groupInfoItem,
361
                                        0,
362
                                        $start,
363
                                        $end,
364
                                        $sessionId
365
                                    );
366
367
                                    api_item_property_update(
368
                                        $this->course,
369
                                        TOOL_CALENDAR_EVENT,
370
                                        $id,
371
                                        'visible',
372
                                        $senderId,
373
                                        $groupInfoItem,
374
                                        0,
375
                                        $start,
376
                                        $end,
377
                                        $sessionId
378
                                    );
379
                                }
380
                            }
381
382
                            // storing the selected users
383
                            if (!empty($sendTo['users'])) {
384
                                foreach ($sendTo['users'] as $userId) {
385
                                    api_item_property_update(
386
                                        $this->course,
387
                                        TOOL_CALENDAR_EVENT,
388
                                        $id,
389
                                        'AgendaAdded',
390
                                        $senderId,
391
                                        $groupInfo,
392
                                        $userId,
393
                                        $start,
394
                                        $end,
395
                                        $sessionId
396
                                    );
397
398
                                    api_item_property_update(
399
                                        $this->course,
400
                                        TOOL_CALENDAR_EVENT,
401
                                        $id,
402
                                        'visible',
403
                                        $senderId,
404
                                        $groupInfo,
405
                                        $userId,
406
                                        $start,
407
                                        $end,
408
                                        $sessionId
409
                                    );
410
                                }
411
                            }
412
                        }
413
                    }
414
415
                    // Add announcement.
416
                    if ($addAsAnnouncement) {
417
                        $this->storeAgendaEventAsAnnouncement(
418
                            $id,
419
                            $usersToSend
420
                        );
421
                    }
422
423
                    // Add attachment.
424
                    if (isset($attachmentArray) && !empty($attachmentArray)) {
425
                        $counter = 0;
426
                        foreach ($attachmentArray as $attachmentItem) {
427
                            $this->addAttachment(
428
                                $id,
429
                                $attachmentItem,
430
                                $attachmentCommentList[$counter],
431
                                $this->course
432
                            );
433
                            $counter++;
434
                        }
435
                    }
436
                }
437
                break;
438
            case 'admin':
439
                if (api_is_platform_admin()) {
440
                    $attributes = [
441
                        'title' => $title,
442
                        'content' => $content,
443
                        'start_date' => $start,
444
                        'end_date' => $end,
445
                        'all_day' => $allDay,
446
                        'access_url_id' => api_get_current_access_url_id(),
447
                    ];
448
449
                    $id = Database::insert(
450
                        $this->tbl_global_agenda,
451
                        $attributes
452
                    );
453
                }
454
                break;
455
        }
456
457
        if (api_get_configuration_value('agenda_reminders')) {
458
            foreach ($reminders as $reminder) {
459
                $this->addReminder($id, $reminder[0], $reminder[1]);
460
            }
461
        }
462
463
        return $id;
464
    }
465
466
    /**
467
     * @throws Exception
468
     */
469
    public function addReminder($eventId, $count, $period)
470
    {
471
        switch ($period) {
472
            case 'i':
473
                $dateInterval = DateInterval::createFromDateString("$count minutes");
474
                break;
475
            case 'h':
476
                $dateInterval = DateInterval::createFromDateString("$count hours");
477
                break;
478
            case 'd':
479
                $dateInterval = DateInterval::createFromDateString("$count days");
480
                break;
481
            case 'w':
482
                $dateInterval = DateInterval::createFromDateString("$count weeks");
483
                break;
484
            default:
485
                return null;
486
        }
487
488
        $agendaReminder = new AgendaReminder();
489
        $agendaReminder
490
            ->setType($this->type)
491
            ->setEventId($eventId)
492
            ->setDateInterval($dateInterval)
493
        ;
494
495
        $em = Database::getManager();
496
        $em->persist($agendaReminder);
497
        $em->flush();
498
    }
499
500
    /**
501
     * @param int $eventId
502
     * @param int $courseId
503
     *
504
     * @return array
505
     */
506
    public function getRepeatedInfoByEvent($eventId, $courseId)
507
    {
508
        $repeatTable = Database::get_course_table(TABLE_AGENDA_REPEAT);
509
        $eventId = (int) $eventId;
510
        $courseId = (int) $courseId;
511
        $sql = "SELECT * FROM $repeatTable
512
                WHERE c_id = $courseId AND cal_id = $eventId";
513
        $res = Database::query($sql);
514
        $repeatInfo = [];
515
        if (Database::num_rows($res) > 0) {
516
            $repeatInfo = Database::fetch_array($res, 'ASSOC');
517
        }
518
519
        return $repeatInfo;
520
    }
521
522
    /**
523
     * @param string $type
524
     * @param string $startEvent      in UTC
525
     * @param string $endEvent        in UTC
526
     * @param string $repeatUntilDate in UTC
527
     *
528
     * @throws Exception
529
     *
530
     * @return array with local times
531
     */
532
    public function generateDatesByType($type, $startEvent, $endEvent, $repeatUntilDate)
533
    {
534
        $continue = true;
535
        $repeatUntilDate = new DateTime($repeatUntilDate, new DateTimeZone('UTC'));
536
        $loopMax = 365;
537
        $counter = 0;
538
        $list = [];
539
540
        switch ($type) {
541
            case 'daily':
542
                $interval = 'P1D';
543
                break;
544
            case 'weekly':
545
                $interval = 'P1W';
546
                break;
547
            case 'monthlyByDate':
548
                $interval = 'P1M';
549
                break;
550
            case 'monthlyByDay':
551
                // not yet implemented
552
                break;
553
            case 'monthlyByDayR':
554
                // not yet implemented
555
                break;
556
            case 'yearly':
557
                $interval = 'P1Y';
558
                break;
559
        }
560
561
        if (empty($interval)) {
562
            return [];
563
        }
564
        $timeZone = api_get_timezone();
565
566
        while ($continue) {
567
            $startDate = new DateTime($startEvent, new DateTimeZone('UTC'));
568
            $endDate = new DateTime($endEvent, new DateTimeZone('UTC'));
569
570
            $startDate->add(new DateInterval($interval));
571
            $endDate->add(new DateInterval($interval));
572
573
            $newStartDate = $startDate->format('Y-m-d H:i:s');
574
            $newEndDate = $endDate->format('Y-m-d H:i:s');
575
576
            $startEvent = $newStartDate;
577
            $endEvent = $newEndDate;
578
579
            if ($endDate > $repeatUntilDate) {
580
                break;
581
            }
582
583
            // @todo remove comment code
584
            // The code below was not adpating to saving light time but was doubling the difference with UTC time.
585
            // Might be necessary to adapt to update saving light time difference.
586
            /*            $startDateInLocal = new DateTime($newStartDate, new DateTimeZone($timeZone));
587
                        if ($startDateInLocal->format('I') == 0) {
588
                            // Is saving time? Then fix UTC time to add time
589
                            $seconds = $startDateInLocal->getOffset();
590
                            $startDate->add(new DateInterval("PT".$seconds."S"));
591
                            //$startDateFixed = $startDate->format('Y-m-d H:i:s');
592
                            //$startDateInLocalFixed = new DateTime($startDateFixed, new DateTimeZone($timeZone));
593
                            //$newStartDate = $startDateInLocalFixed->format('Y-m-d H:i:s');
594
                            //$newStartDate = $startDate->setTimezone(new DateTimeZone($timeZone))->format('Y-m-d H:i:s');
595
                        }
596
597
                        $endDateInLocal = new DateTime($newEndDate, new DateTimeZone($timeZone));
598
                        if ($endDateInLocal->format('I') == 0) {
599
                            // Is saving time? Then fix UTC time to add time
600
                            $seconds = $endDateInLocal->getOffset();
601
                            $endDate->add(new DateInterval("PT".$seconds."S"));
602
                            //$endDateFixed = $endDate->format('Y-m-d H:i:s');
603
                            //$endDateInLocalFixed = new DateTime($endDateFixed, new DateTimeZone($timeZone));
604
                            //$newEndDate = $endDateInLocalFixed->format('Y-m-d H:i:s');
605
                    }
606
            */
607
            $newStartDate = $startDate->setTimezone(new DateTimeZone($timeZone))->format('Y-m-d H:i:s');
608
            $newEndDate = $endDate->setTimezone(new DateTimeZone($timeZone))->format('Y-m-d H:i:s');
609
            $list[] = ['start' => $newStartDate, 'end' => $newEndDate];
610
            $counter++;
611
612
            // just in case stop if more than $loopMax
613
            if ($counter > $loopMax) {
614
                break;
615
            }
616
        }
617
618
        return $list;
619
    }
620
621
    /**
622
     * @param int    $eventId
623
     * @param string $type
624
     * @param string $end     in UTC
625
     * @param array  $sentTo
626
     *
627
     * @return bool
628
     */
629
    public function addRepeatedItem($eventId, $type, $end, $sentTo = [])
630
    {
631
        $t_agenda = Database::get_course_table(TABLE_AGENDA);
632
        $t_agenda_r = Database::get_course_table(TABLE_AGENDA_REPEAT);
633
634
        if (empty($this->course)) {
635
            return false;
636
        }
637
638
        $courseId = $this->course['real_id'];
639
        $eventId = (int) $eventId;
640
641
        $sql = "SELECT title, content, start_date, end_date, all_day
642
                FROM $t_agenda
643
                WHERE c_id = $courseId AND id = $eventId";
644
        $res = Database::query($sql);
645
646
        if (Database::num_rows($res) !== 1) {
647
            return false;
648
        }
649
650
        $typeList = [
651
            'daily',
652
            'weekly',
653
            'monthlyByDate',
654
            'monthlyByDay',
655
            'monthlyByDayR',
656
            'yearly',
657
        ];
658
659
        if (!in_array($type, $typeList)) {
660
            return false;
661
        }
662
663
        $now = time();
664
665
        // The event has to repeat *in the future*. We don't allow repeated
666
        // events in the past.
667
        $endTimeStamp = api_strtotime($end, 'UTC');
668
669
        if ($endTimeStamp < $now) {
670
            return false;
671
        }
672
673
        $row = Database::fetch_array($res);
674
675
        $title = $row['title'];
676
        $content = $row['content'];
677
        $allDay = $row['all_day'];
678
679
        $type = Database::escape_string($type);
680
        $end = Database::escape_string($end);
681
682
        $sql = "INSERT INTO $t_agenda_r (c_id, cal_id, cal_type, cal_end)
683
                VALUES ($courseId, '$eventId', '$type', '$endTimeStamp')";
684
        Database::query($sql);
685
686
        $generatedDates = $this->generateDatesByType($type, $row['start_date'], $row['end_date'], $end);
687
688
        if (empty($generatedDates)) {
689
            return false;
690
        }
691
692
        foreach ($generatedDates as $dateInfo) {
693
//            $start = api_get_local_time($dateInfo['start']);
694
//            $end = api_get_local_time($dateInfo['end']);
695
            // On line 529 in function generateDatesByType there is a @todo remove comment code
696
            // just before the part updating the date in local time so keep both synchronised
697
            $start = $dateInfo['start'];
698
            $end = $dateInfo['end'];
699
700
            $this->addEvent(
701
                $start,
702
                $end,
703
                $allDay,
704
                $title,
705
                $content,
706
                $sentTo,
707
                false,
708
                $eventId
709
            );
710
        }
711
712
        return true;
713
    }
714
715
    /**
716
     * @param int   $item_id
717
     * @param array $sentTo
718
     *
719
     * @return int
720
     */
721
    public function storeAgendaEventAsAnnouncement($item_id, $sentTo = [])
722
    {
723
        $table_agenda = Database::get_course_table(TABLE_AGENDA);
724
        $courseId = api_get_course_int_id();
725
726
        // Check params
727
        if (empty($item_id) || $item_id != strval(intval($item_id))) {
728
            return -1;
729
        }
730
731
        // Get the agenda item.
732
        $item_id = intval($item_id);
733
        $sql = "SELECT * FROM $table_agenda
734
                WHERE c_id = $courseId AND id = ".$item_id;
735
        $res = Database::query($sql);
736
737
        if (Database::num_rows($res) > 0) {
738
            $row = Database::fetch_array($res, 'ASSOC');
739
740
            // Sending announcement
741
            if (!empty($sentTo)) {
742
                $id = AnnouncementManager::add_announcement(
743
                    api_get_course_info(),
744
                    api_get_session_id(),
745
                    $row['title'],
746
                    $row['content'],
747
                    $sentTo,
748
                    null,
749
                    null,
750
                    $row['end_date']
751
                );
752
753
                AnnouncementManager::sendEmail(
754
                    api_get_course_info(),
755
                    api_get_session_id(),
756
                    $id
757
                );
758
759
                return $id;
760
            }
761
        }
762
763
        return -1;
764
    }
765
766
    /**
767
     * Edits an event.
768
     *
769
     * @param int    $id
770
     * @param string $start                 datetime format: 2012-06-14 09:00:00
771
     * @param string $end                   datetime format: 2012-06-14 09:00:00
772
     * @param int    $allDay                is all day 'true' or 'false'
773
     * @param string $title
774
     * @param string $content
775
     * @param array  $usersToSend
776
     * @param array  $attachmentArray
777
     * @param array  $attachmentCommentList
778
     * @param string $comment
779
     * @param string $color
780
     * @param bool   $addAnnouncement
781
     * @param bool   $updateContent
782
     * @param int    $authorId
783
     *
784
     * @return bool
785
     */
786
    public function editEvent(
787
        $id,
788
        $start,
789
        $end,
790
        $allDay,
791
        $title,
792
        $content,
793
        $usersToSend = [],
794
        $attachmentArray = [],
795
        $attachmentCommentList = [],
796
        $comment = null,
797
        $color = '',
798
        $addAnnouncement = false,
799
        $updateContent = true,
800
        $authorId = 0,
801
        array $inviteesList = [],
802
        bool $isCollective = false
803
    ) {
804
        $id = (int) $id;
805
        $start = api_get_utc_datetime($start);
806
        $end = api_get_utc_datetime($end);
807
        $allDay = isset($allDay) && $allDay == 'true' ? 1 : 0;
808
        $currentUserId = api_get_user_id();
809
        $authorId = empty($authorId) ? $currentUserId : (int) $authorId;
810
811
        switch ($this->type) {
812
            case 'personal':
813
                $eventInfo = $this->get_event($id);
814
                if ($eventInfo['user'] != $currentUserId
815
                    && (
816
                        api_get_configuration_value('agenda_collective_invitations')
817
                            && !self::isUserInvitedInEvent($id, $currentUserId)
818
                    )
819
                ) {
820
                    break;
821
                }
822
                $attributes = [
823
                    'title' => $title,
824
                    'date' => $start,
825
                    'enddate' => $end,
826
                    'all_day' => $allDay,
827
                ];
828
829
                if ($updateContent) {
830
                    $attributes['text'] = $content;
831
                }
832
833
                if (!empty($color)) {
834
                    $attributes['color'] = $color;
835
                }
836
837
                Database::update(
838
                    $this->tbl_personal_agenda,
839
                    $attributes,
840
                    ['id = ?' => $id]
841
                );
842
843
                if (api_get_configuration_value('agenda_collective_invitations')) {
844
                    Agenda::saveCollectiveProperties($inviteesList, $isCollective, $id);
845
                }
846
                break;
847
            case 'course':
848
                $eventInfo = $this->get_event($id);
849
850
                if (empty($eventInfo)) {
851
                    return false;
852
                }
853
854
                $groupId = api_get_group_id();
855
                $groupIid = 0;
856
                $groupInfo = [];
857
                if ($groupId) {
858
                    $groupInfo = GroupManager::get_group_properties($groupId);
859
                    if ($groupInfo) {
860
                        $groupIid = $groupInfo['iid'];
861
                    }
862
                }
863
864
                $courseId = $this->course['real_id'];
865
866
                if (empty($courseId)) {
867
                    return false;
868
                }
869
870
                if ($this->getIsAllowedToEdit()) {
871
                    $attributes = [
872
                        'title' => $title,
873
                        'start_date' => $start,
874
                        'end_date' => $end,
875
                        'all_day' => $allDay,
876
                        'comment' => $comment,
877
                    ];
878
879
                    if ($updateContent) {
880
                        $attributes['content'] = $content;
881
                    }
882
883
                    if (!empty($color)) {
884
                        $attributes['color'] = $color;
885
                    }
886
887
                    Database::update(
888
                        $this->tbl_course_agenda,
889
                        $attributes,
890
                        [
891
                            'id = ? AND c_id = ? AND session_id = ? ' => [
892
                                $id,
893
                                $courseId,
894
                                $this->sessionId,
895
                            ],
896
                        ]
897
                    );
898
899
                    if (!empty($usersToSend)) {
900
                        $sendTo = $this->parseSendToArray($usersToSend);
901
902
                        $usersToDelete = array_diff(
903
                            $eventInfo['send_to']['users'],
904
                            $sendTo['users']
905
                        );
906
                        $usersToAdd = array_diff(
907
                            $sendTo['users'],
908
                            $eventInfo['send_to']['users']
909
                        );
910
911
                        $groupsToDelete = array_diff(
912
                            $eventInfo['send_to']['groups'],
913
                            $sendTo['groups']
914
                        );
915
                        $groupToAdd = array_diff(
916
                            $sendTo['groups'],
917
                            $eventInfo['send_to']['groups']
918
                        );
919
920
                        if ($sendTo['everyone']) {
921
                            // Delete all from group
922
                            if (isset($eventInfo['send_to']['groups']) &&
923
                                !empty($eventInfo['send_to']['groups'])
924
                            ) {
925
                                foreach ($eventInfo['send_to']['groups'] as $group) {
926
                                    $groupIidItem = 0;
927
                                    if ($group) {
928
                                        $groupInfoItem = GroupManager::get_group_properties(
929
                                            $group
930
                                        );
931
                                        if ($groupInfoItem) {
932
                                            $groupIidItem = $groupInfoItem['iid'];
933
                                        }
934
                                    }
935
936
                                    api_item_property_delete(
937
                                        $this->course,
938
                                        TOOL_CALENDAR_EVENT,
939
                                        $id,
940
                                        0,
941
                                        $groupIidItem,
942
                                        $this->sessionId
943
                                    );
944
                                }
945
                            }
946
947
                            // Storing the selected users.
948
                            if (isset($eventInfo['send_to']['users']) &&
949
                                !empty($eventInfo['send_to']['users'])
950
                            ) {
951
                                foreach ($eventInfo['send_to']['users'] as $userId) {
952
                                    api_item_property_delete(
953
                                        $this->course,
954
                                        TOOL_CALENDAR_EVENT,
955
                                        $id,
956
                                        $userId,
957
                                        $groupIid,
958
                                        $this->sessionId
959
                                    );
960
                                }
961
                            }
962
963
                            // Add to everyone only.
964
                            api_item_property_update(
965
                                $this->course,
966
                                TOOL_CALENDAR_EVENT,
967
                                $id,
968
                                'visible',
969
                                $authorId,
970
                                $groupInfo,
971
                                null,
972
                                $start,
973
                                $end,
974
                                $this->sessionId
975
                            );
976
                        } else {
977
                            // Delete "everyone".
978
                            api_item_property_delete(
979
                                $this->course,
980
                                TOOL_CALENDAR_EVENT,
981
                                $id,
982
                                0,
983
                                0,
984
                                $this->sessionId
985
                            );
986
987
                            // Add groups
988
                            if (!empty($groupToAdd)) {
989
                                foreach ($groupToAdd as $group) {
990
                                    $groupInfoItem = [];
991
                                    if ($group) {
992
                                        $groupInfoItem = GroupManager::get_group_properties(
993
                                            $group
994
                                        );
995
                                    }
996
997
                                    api_item_property_update(
998
                                        $this->course,
999
                                        TOOL_CALENDAR_EVENT,
1000
                                        $id,
1001
                                        'visible',
1002
                                        $authorId,
1003
                                        $groupInfoItem,
1004
                                        0,
1005
                                        $start,
1006
                                        $end,
1007
                                        $this->sessionId
1008
                                    );
1009
                                }
1010
                            }
1011
1012
                            // Delete groups.
1013
                            if (!empty($groupsToDelete)) {
1014
                                foreach ($groupsToDelete as $group) {
1015
                                    $groupIidItem = 0;
1016
                                    $groupInfoItem = [];
1017
                                    if ($group) {
1018
                                        $groupInfoItem = GroupManager::get_group_properties(
1019
                                            $group
1020
                                        );
1021
                                        if ($groupInfoItem) {
1022
                                            $groupIidItem = $groupInfoItem['iid'];
1023
                                        }
1024
                                    }
1025
1026
                                    api_item_property_delete(
1027
                                        $this->course,
1028
                                        TOOL_CALENDAR_EVENT,
1029
                                        $id,
1030
                                        0,
1031
                                        $groupIidItem,
1032
                                        $this->sessionId
1033
                                    );
1034
                                }
1035
                            }
1036
1037
                            // Add users.
1038
                            if (!empty($usersToAdd)) {
1039
                                foreach ($usersToAdd as $userId) {
1040
                                    api_item_property_update(
1041
                                        $this->course,
1042
                                        TOOL_CALENDAR_EVENT,
1043
                                        $id,
1044
                                        'visible',
1045
                                        $authorId,
1046
                                        $groupInfo,
1047
                                        $userId,
1048
                                        $start,
1049
                                        $end,
1050
                                        $this->sessionId
1051
                                    );
1052
                                }
1053
                            }
1054
1055
                            // Delete users.
1056
                            if (!empty($usersToDelete)) {
1057
                                foreach ($usersToDelete as $userId) {
1058
                                    api_item_property_delete(
1059
                                        $this->course,
1060
                                        TOOL_CALENDAR_EVENT,
1061
                                        $id,
1062
                                        $userId,
1063
                                        $groupInfo,
1064
                                        $this->sessionId
1065
                                    );
1066
                                }
1067
                            }
1068
                        }
1069
                    }
1070
1071
                    // Add announcement.
1072
                    if (isset($addAnnouncement) && !empty($addAnnouncement)) {
1073
                        $this->storeAgendaEventAsAnnouncement(
1074
                            $id,
1075
                            $usersToSend
1076
                        );
1077
                    }
1078
1079
                    // Add attachment.
1080
                    if (isset($attachmentArray) && !empty($attachmentArray)) {
1081
                        $counter = 0;
1082
                        foreach ($attachmentArray as $attachmentItem) {
1083
                            $this->updateAttachment(
1084
                                $attachmentItem['id'],
1085
                                $id,
1086
                                $attachmentItem,
1087
                                $attachmentCommentList[$counter],
1088
                                $this->course
1089
                            );
1090
                            $counter++;
1091
                        }
1092
                    }
1093
1094
                    return true;
1095
                } else {
1096
                    return false;
1097
                }
1098
                break;
1099
            case 'admin':
1100
            case 'platform':
1101
                if (api_is_platform_admin()) {
1102
                    $attributes = [
1103
                        'title' => $title,
1104
                        'start_date' => $start,
1105
                        'end_date' => $end,
1106
                        'all_day' => $allDay,
1107
                    ];
1108
1109
                    if ($updateContent) {
1110
                        $attributes['content'] = $content;
1111
                    }
1112
                    Database::update(
1113
                        $this->tbl_global_agenda,
1114
                        $attributes,
1115
                        ['id = ?' => $id]
1116
                    );
1117
                }
1118
                break;
1119
        }
1120
    }
1121
1122
    /**
1123
     * @param int  $id
1124
     * @param bool $deleteAllItemsFromSerie
1125
     *
1126
     * @throws \Doctrine\ORM\ORMException
1127
     * @throws \Doctrine\ORM\OptimisticLockException
1128
     */
1129
    public function deleteEvent($id, $deleteAllItemsFromSerie = false)
1130
    {
1131
        $em = Database::getManager();
1132
1133
        switch ($this->type) {
1134
            case 'personal':
1135
                $eventInfo = $this->get_event($id);
1136
                if ($eventInfo['user'] == api_get_user_id()) {
1137
                    Database::delete(
1138
                        $this->tbl_personal_agenda,
1139
                        ['id = ?' => $id]
1140
                    );
1141
                } elseif (api_get_configuration_value('agenda_collective_invitations')) {
1142
                    $currentUser = api_get_user_entity(api_get_user_id());
1143
1144
                    $eventRepo = $em->getRepository('ChamiloCoreBundle:PersonalAgenda');
1145
                    $event = $eventRepo->findOneByIdAndInvitee($id, $currentUser);
1146
                    $invitation = $event ? $event->getInvitation() : null;
1147
1148
                    if ($invitation) {
1149
                        $invitation->removeInviteeUser($currentUser);
1150
1151
                        $em->persist($invitation);
1152
                        $em->flush();
1153
                    }
1154
                }
1155
                break;
1156
            case 'course':
1157
                $courseId = api_get_course_int_id();
1158
                $isAllowToEdit = $this->getIsAllowedToEdit();
1159
1160
                if (!empty($courseId) && $isAllowToEdit) {
1161
                    $eventInfo = $this->get_event($id);
1162
                    if ($deleteAllItemsFromSerie) {
1163
                        /* This is one of the children.
1164
                           Getting siblings and delete 'Em all + the father! */
1165
                        if (isset($eventInfo['parent_event_id']) && !empty($eventInfo['parent_event_id'])) {
1166
                            // Removing items.
1167
                            $events = $this->getAllRepeatEvents($eventInfo['parent_event_id']);
1168
                            if (!empty($events)) {
1169
                                foreach ($events as $event) {
1170
                                    $this->deleteEvent($event['id']);
1171
                                }
1172
                            }
1173
                            // Removing parent.
1174
                            $this->deleteEvent($eventInfo['parent_event_id']);
1175
                        } else {
1176
                            // This is the father looking for the children.
1177
                            $events = $this->getAllRepeatEvents($id);
1178
                            if (!empty($events)) {
1179
                                foreach ($events as $event) {
1180
                                    $this->deleteEvent($event['id']);
1181
                                }
1182
                            }
1183
                        }
1184
                    }
1185
1186
                    // Removing from events.
1187
                    Database::delete(
1188
                        $this->tbl_course_agenda,
1189
                        ['id = ? AND c_id = ?' => [$id, $courseId]]
1190
                    );
1191
1192
                    api_item_property_update(
1193
                        $this->course,
1194
                        TOOL_CALENDAR_EVENT,
1195
                        $id,
1196
                        'delete',
1197
                        api_get_user_id()
1198
                    );
1199
1200
                    // Removing from series.
1201
                    Database::delete(
1202
                        $this->table_repeat,
1203
                        [
1204
                            'cal_id = ? AND c_id = ?' => [
1205
                                $id,
1206
                                $courseId,
1207
                            ],
1208
                        ]
1209
                    );
1210
1211
                    if (isset($eventInfo['attachment']) && !empty($eventInfo['attachment'])) {
1212
                        foreach ($eventInfo['attachment'] as $attachment) {
1213
                            self::deleteAttachmentFile(
1214
                                $attachment['id'],
1215
                                $this->course
1216
                            );
1217
                        }
1218
                    }
1219
                }
1220
                break;
1221
            case 'admin':
1222
                if (api_is_platform_admin()) {
1223
                    Database::delete(
1224
                        $this->tbl_global_agenda,
1225
                        ['id = ?' => $id]
1226
                    );
1227
                }
1228
                break;
1229
        }
1230
    }
1231
1232
    /**
1233
     * Get agenda events.
1234
     *
1235
     * @param int    $start
1236
     * @param int    $end
1237
     * @param int    $courseId
1238
     * @param int    $groupId
1239
     * @param int    $user_id
1240
     * @param string $format
1241
     *
1242
     * @return array|string
1243
     */
1244
    public function getEvents(
1245
        $start,
1246
        $end,
1247
        $courseId = null,
1248
        $groupId = null,
1249
        $user_id = 0,
1250
        $format = 'json'
1251
    ) {
1252
        switch ($this->type) {
1253
            case 'admin':
1254
                $this->getPlatformEvents($start, $end);
1255
                break;
1256
            case 'course':
1257
                $courseInfo = api_get_course_info_by_id($courseId);
1258
1259
                // Session coach can see all events inside a session.
1260
                if (api_is_coach()) {
1261
                    // Own course
1262
                    $this->getCourseEvents(
1263
                        $start,
1264
                        $end,
1265
                        $courseInfo,
1266
                        $groupId,
1267
                        $this->sessionId,
1268
                        $user_id
1269
                    );
1270
1271
                    // Others
1272
                    $this->getSessionEvents(
1273
                        $start,
1274
                        $end,
1275
                        $this->sessionId,
1276
                        $user_id,
1277
                        $this->eventOtherSessionColor
1278
                    );
1279
                } else {
1280
                    $this->getCourseEvents(
1281
                        $start,
1282
                        $end,
1283
                        $courseInfo,
1284
                        $groupId,
1285
                        $this->sessionId,
1286
                        $user_id
1287
                    );
1288
                }
1289
                break;
1290
            case 'personal':
1291
            default:
1292
                $sessionFilterActive = false;
1293
                if (!empty($this->sessionId)) {
1294
                    $sessionFilterActive = true;
1295
                }
1296
1297
                if ($sessionFilterActive == false) {
1298
                    // Getting personal events
1299
                    $this->getPersonalEvents($start, $end);
1300
1301
                    // Getting platform/admin events
1302
                    $this->getPlatformEvents($start, $end);
1303
                }
1304
1305
                $ignoreVisibility = api_get_configuration_value('personal_agenda_show_all_session_events');
1306
1307
                $session_list = [];
1308
                // Getting course events
1309
                $my_course_list = [];
1310
                if (!api_is_anonymous()) {
1311
                    $session_list = SessionManager::get_sessions_by_user(
1312
                        api_get_user_id(),
1313
                        $ignoreVisibility
1314
                    );
1315
                    $my_course_list = CourseManager::get_courses_list_by_user_id(
1316
                        api_get_user_id(),
1317
                        false
1318
                    );
1319
                }
1320
1321
                if (api_is_drh()) {
1322
                    if (api_drh_can_access_all_session_content()) {
1323
                        $session_list = [];
1324
                        $sessionList = SessionManager::get_sessions_followed_by_drh(
1325
                            api_get_user_id(),
1326
                            null,
1327
                            null,
1328
                            null,
1329
                            true,
1330
                            false
1331
                        );
1332
1333
                        if (!empty($sessionList)) {
1334
                            foreach ($sessionList as $sessionItem) {
1335
                                $sessionId = $sessionItem['id'];
1336
                                $courses = SessionManager::get_course_list_by_session_id($sessionId);
1337
                                $sessionInfo = [
1338
                                    'session_id' => $sessionId,
1339
                                    'courses' => $courses,
1340
                                ];
1341
                                $session_list[] = $sessionInfo;
1342
                            }
1343
                        }
1344
                    }
1345
                }
1346
1347
                if (!empty($session_list)) {
1348
                    foreach ($session_list as $session_item) {
1349
                        if ($sessionFilterActive) {
1350
                            if ($this->sessionId != $session_item['session_id']) {
1351
                                continue;
1352
                            }
1353
                        }
1354
1355
                        $my_courses = $session_item['courses'];
1356
                        $my_session_id = $session_item['session_id'];
1357
1358
                        if (!empty($my_courses)) {
1359
                            foreach ($my_courses as $course_item) {
1360
                                $courseInfo = api_get_course_info_by_id(
1361
                                    $course_item['real_id']
1362
                                );
1363
                                $this->getCourseEvents(
1364
                                    $start,
1365
                                    $end,
1366
                                    $courseInfo,
1367
                                    0,
1368
                                    $my_session_id
1369
                                );
1370
                            }
1371
                        }
1372
                    }
1373
                }
1374
1375
                if (!empty($my_course_list) && $sessionFilterActive == false) {
1376
                    foreach ($my_course_list as $courseInfoItem) {
1377
                        $courseInfo = api_get_course_info_by_id(
1378
                            $courseInfoItem['real_id']
1379
                        );
1380
                        if (isset($courseId) && !empty($courseId)) {
1381
                            if ($courseInfo['real_id'] == $courseId) {
1382
                                $this->getCourseEvents(
1383
                                    $start,
1384
                                    $end,
1385
                                    $courseInfo,
1386
                                    0,
1387
                                    0,
1388
                                    $user_id
1389
                                );
1390
                            }
1391
                        } else {
1392
                            $this->getCourseEvents(
1393
                                $start,
1394
                                $end,
1395
                                $courseInfo,
1396
                                0,
1397
                                0,
1398
                                $user_id
1399
                            );
1400
                        }
1401
                    }
1402
                }
1403
1404
                if ($start && $end) {
1405
                    $this->loadSessionsAsEvents($start, $end);
1406
                }
1407
1408
                break;
1409
        }
1410
1411
        $this->cleanEvents();
1412
1413
        switch ($format) {
1414
            case 'json':
1415
                if (empty($this->events)) {
1416
                    return '[]';
1417
                }
1418
1419
                return json_encode($this->events);
1420
                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...
1421
            case 'array':
1422
                if (empty($this->events)) {
1423
                    return [];
1424
                }
1425
1426
                return $this->events;
1427
                break;
1428
        }
1429
    }
1430
1431
    /**
1432
     * Clean events.
1433
     *
1434
     * @return bool
1435
     */
1436
    public function cleanEvents()
1437
    {
1438
        if (empty($this->events)) {
1439
            return false;
1440
        }
1441
1442
        foreach ($this->events as &$event) {
1443
            $event['description'] = Security::remove_XSS($event['description']);
1444
            $event['title'] = Security::remove_XSS($event['title']);
1445
        }
1446
1447
        return true;
1448
    }
1449
1450
    /**
1451
     * @param int $id
1452
     * @param int $minute_delta
1453
     *
1454
     * @return int
1455
     */
1456
    public function resizeEvent($id, $minute_delta)
1457
    {
1458
        $id = (int) $id;
1459
        $delta = (int) $minute_delta;
1460
        $event = $this->get_event($id);
1461
        if (!empty($event)) {
1462
            switch ($this->type) {
1463
                case 'personal':
1464
                    $sql = "UPDATE $this->tbl_personal_agenda SET
1465
                            enddate = DATE_ADD(enddate, INTERVAL $delta MINUTE)
1466
							WHERE id = ".$id;
1467
                    Database::query($sql);
1468
                    break;
1469
                case 'course':
1470
                    $sql = "UPDATE $this->tbl_course_agenda SET
1471
                            end_date = DATE_ADD(end_date, INTERVAL $delta MINUTE)
1472
							WHERE
1473
							    c_id = ".$this->course['real_id']." AND
1474
							    id = ".$id;
1475
                    Database::query($sql);
1476
                    break;
1477
                case 'admin':
1478
                    $sql = "UPDATE $this->tbl_global_agenda SET
1479
                            end_date = DATE_ADD(end_date, INTERVAL $delta MINUTE)
1480
							WHERE id = ".$id;
1481
                    Database::query($sql);
1482
                    break;
1483
            }
1484
        }
1485
1486
        return 1;
1487
    }
1488
1489
    /**
1490
     * @param int $id
1491
     * @param int $minute_delta minutes
1492
     * @param int $allDay
1493
     *
1494
     * @return int
1495
     */
1496
    public function move_event($id, $minute_delta, $allDay)
1497
    {
1498
        $id = (int) $id;
1499
        $event = $this->get_event($id);
1500
1501
        if (empty($event)) {
1502
            return false;
1503
        }
1504
1505
        // we convert the hour delta into minutes and add the minute delta
1506
        $delta = (int) $minute_delta;
1507
        $allDay = (int) $allDay;
1508
1509
        if (!empty($event)) {
1510
            switch ($this->type) {
1511
                case 'personal':
1512
                    $sql = "UPDATE $this->tbl_personal_agenda SET
1513
                            all_day = $allDay, date = DATE_ADD(date, INTERVAL $delta MINUTE),
1514
                            enddate = DATE_ADD(enddate, INTERVAL $delta MINUTE)
1515
							WHERE id=".$id;
1516
                    Database::query($sql);
1517
                    break;
1518
                case 'course':
1519
                    $sql = "UPDATE $this->tbl_course_agenda SET
1520
                            all_day = $allDay,
1521
                            start_date = DATE_ADD(start_date, INTERVAL $delta MINUTE),
1522
                            end_date = DATE_ADD(end_date, INTERVAL $delta MINUTE)
1523
							WHERE
1524
							    c_id = ".$this->course['real_id']." AND
1525
							    id=".$id;
1526
                    Database::query($sql);
1527
                    break;
1528
                case 'admin':
1529
                    $sql = "UPDATE $this->tbl_global_agenda SET
1530
                            all_day = $allDay,
1531
                            start_date = DATE_ADD(start_date,INTERVAL $delta MINUTE),
1532
                            end_date = DATE_ADD(end_date, INTERVAL $delta MINUTE)
1533
							WHERE id=".$id;
1534
                    Database::query($sql);
1535
                    break;
1536
            }
1537
        }
1538
1539
        return 1;
1540
    }
1541
1542
    /**
1543
     * Gets a single event.
1544
     *
1545
     * @param int $id event id
1546
     *
1547
     * @return array
1548
     */
1549
    public function get_event($id)
1550
    {
1551
        // make sure events of the personal agenda can only be seen by the user himself
1552
        $id = (int) $id;
1553
        $event = null;
1554
        $agendaCollectiveInvitations = api_get_configuration_value('agenda_collective_invitations');
1555
1556
        switch ($this->type) {
1557
            case 'personal':
1558
                $user = api_get_user_entity(api_get_user_id());
1559
                $sql = "SELECT * FROM ".$this->tbl_personal_agenda."
1560
                        WHERE id = $id AND user = ".$user->getId();
1561
                $result = Database::query($sql);
1562
                if (Database::num_rows($result)) {
1563
                    $event = Database::fetch_array($result, 'ASSOC');
1564
                    $event['description'] = $event['text'];
1565
                    $event['content'] = $event['text'];
1566
                    $event['start_date'] = $event['date'];
1567
                    $event['end_date'] = $event['enddate'];
1568
                }
1569
1570
                if (null !== $event) {
1571
                    return $event;
1572
                }
1573
1574
                if ($agendaCollectiveInvitations) {
1575
                    $eventRepo = Database::getManager()->getRepository('ChamiloCoreBundle:PersonalAgenda');
1576
                    $event = $eventRepo->findOneByIdAndInvitee($id, $user);
1577
1578
                    if ($event && $event->isCollective()) {
1579
                        return [
1580
                            'id' => $event->getId(),
1581
                            'user' => $event->getUser(),
1582
                            'title' => $event->getTitle(),
1583
                            'text' => $event->getText(),
1584
                            'date' => $event->getDate()->format('Y-m-d H:i:s'),
1585
                            'enddate' => $event->getEndDate()->format('Y-m-d H:i:s'),
1586
                            'course' => null,
1587
                            'parent_event_id' => $event->getParentEventId(),
1588
                            'all_day' => $event->getAllDay(),
1589
                            'color' => $event->getColor(),
1590
                            'agenda_event_invitation_id' => $event->getInvitation()->getId(),
1591
                            'collective' => $event->isCollective(),
1592
                            'description' => $event->getText(),
1593
                            'content' => $event->getText(),
1594
                            'start_date' => $event->getDate()->format('Y-m-d H:i:s'),
1595
                            'end_date' => $event->getEndDate()->format('Y-m-d H:i:s'),
1596
                        ];
1597
                    }
1598
                }
1599
1600
                return null;
1601
            case 'course':
1602
                if (!empty($this->course['real_id'])) {
1603
                    $sql = "SELECT * FROM ".$this->tbl_course_agenda."
1604
                            WHERE c_id = ".$this->course['real_id']." AND id = ".$id;
1605
                    $result = Database::query($sql);
1606
                    if (Database::num_rows($result)) {
1607
                        $event = Database::fetch_array($result, 'ASSOC');
1608
                        $event['description'] = $event['content'];
1609
1610
                        // Getting send to array
1611
                        $event['send_to'] = $this->getUsersAndGroupSubscribedToEvent(
1612
                            $id,
1613
                            $this->course['real_id'],
1614
                            $this->sessionId
1615
                        );
1616
1617
                        // Getting repeat info
1618
                        $event['repeat_info'] = $this->getRepeatedInfoByEvent(
1619
                            $id,
1620
                            $this->course['real_id']
1621
                        );
1622
1623
                        if (!empty($event['parent_event_id'])) {
1624
                            $event['parent_info'] = $this->get_event($event['parent_event_id']);
1625
                        }
1626
1627
                        $event['attachment'] = $this->getAttachmentList(
1628
                            $id,
1629
                            $this->course
1630
                        );
1631
                    }
1632
                }
1633
                break;
1634
            case 'admin':
1635
            case 'platform':
1636
                $sql = "SELECT * FROM ".$this->tbl_global_agenda."
1637
                        WHERE id = $id";
1638
                $result = Database::query($sql);
1639
                if (Database::num_rows($result)) {
1640
                    $event = Database::fetch_array($result, 'ASSOC');
1641
                    $event['description'] = $event['content'];
1642
                }
1643
                break;
1644
        }
1645
1646
        return $event;
1647
    }
1648
1649
    /**
1650
     * Gets personal events.
1651
     *
1652
     * @param int $start
1653
     * @param int $end
1654
     *
1655
     * @return array
1656
     */
1657
    public function getPersonalEvents($start, $end)
1658
    {
1659
        $start = (int) $start;
1660
        $end = (int) $end;
1661
        $startDate = null;
1662
        $endDate = null;
1663
        $startCondition = '';
1664
        $endCondition = '';
1665
1666
        $em = Database::getManager();
1667
        $agendaCollectiveInvitations = api_get_configuration_value('agenda_collective_invitations');
1668
        $inviteeRepo = null;
1669
        if ($agendaCollectiveInvitations) {
1670
            $inviteeRepo = $em->getRepository('ChamiloCoreBundle:AgendaEventInvitee');
1671
        }
1672
        if ($start !== 0) {
1673
            $startDate = api_get_utc_datetime($start, true, true);
1674
            $startCondition = "AND date >= '".$startDate->format('Y-m-d H:i:s')."'";
1675
        }
1676
        if ($start !== 0) {
1677
            $endDate = api_get_utc_datetime($end, false, true);
1678
            $endCondition = "AND (enddate <= '".$endDate->format('Y-m-d H:i:s')."' OR enddate IS NULL)";
1679
        }
1680
        $user_id = api_get_user_id();
1681
1682
        $sql = "SELECT * FROM ".$this->tbl_personal_agenda."
1683
                WHERE user = $user_id $startCondition $endCondition";
1684
1685
        $result = Database::query($sql);
1686
        $my_events = [];
1687
        if (Database::num_rows($result)) {
1688
            while ($row = Database::fetch_array($result, 'ASSOC')) {
1689
                $event = [];
1690
                $event['id'] = 'personal_'.$row['id'];
1691
                $event['title'] = $row['title'];
1692
                $event['className'] = 'personal';
1693
                $event['borderColor'] = $event['backgroundColor'] = $this->event_personal_color;
1694
                $event['editable'] = true;
1695
                $event['sent_to'] = get_lang('Me');
1696
                $event['type'] = 'personal';
1697
1698
                if (!empty($row['date'])) {
1699
                    $event['start'] = $this->formatEventDate($row['date']);
1700
                    $event['start_date_localtime'] = api_get_local_time($row['date']);
1701
                }
1702
1703
                if (!empty($row['enddate'])) {
1704
                    $event['end'] = $this->formatEventDate($row['enddate']);
1705
                    $event['end_date_localtime'] = api_get_local_time($row['enddate']);
1706
                }
1707
1708
                $event['description'] = $row['text'];
1709
                $event['allDay'] = isset($row['all_day']) && $row['all_day'] == 1 ? $row['all_day'] : 0;
1710
                $event['parent_event_id'] = 0;
1711
                $event['has_children'] = 0;
1712
1713
                if ($agendaCollectiveInvitations) {
1714
                    $event['collective'] = (bool) $row['collective'];
1715
                    $event['invitees'] = self::getInviteesForPersonalEvent($row['id']);
1716
                }
1717
1718
                $my_events[] = $event;
1719
                $this->events[] = $event;
1720
            }
1721
        }
1722
1723
        if ($agendaCollectiveInvitations) {
1724
            $this->loadEventsAsInvitee(
1725
                api_get_user_entity($user_id),
1726
                $startDate,
1727
                $endDate
1728
            );
1729
        }
1730
1731
        // Add plugin personal events
1732
1733
        $this->plugin = new AppPlugin();
1734
        $plugins = $this->plugin->getInstalledPluginListObject();
1735
        /** @var Plugin $plugin */
1736
        foreach ($plugins as $plugin) {
1737
            if ($plugin->hasPersonalEvents && method_exists($plugin, 'getPersonalEvents')) {
1738
                $pluginEvents = $plugin->getPersonalEvents($this, $start, $end);
1739
1740
                if (!empty($pluginEvents)) {
1741
                    $this->events = array_merge($this->events, $pluginEvents);
1742
                }
1743
            }
1744
        }
1745
1746
        return $my_events;
1747
    }
1748
1749
    public static function getInviteesForPersonalEvent($eventId): array
1750
    {
1751
        $em = Database::getManager();
1752
        $event = $em->find('ChamiloCoreBundle:PersonalAgenda', $eventId);
1753
1754
        $inviteeRepo = $em->getRepository('ChamiloCoreBundle:AgendaEventInvitee');
1755
        $invitees = $inviteeRepo->findByInvitation($event->getInvitation());
1756
1757
        $inviteeList = [];
1758
1759
        foreach ($invitees as $invitee) {
1760
            $inviteeUser = $invitee->getUser();
1761
1762
            $inviteeList[] = [
1763
                'id' => $inviteeUser->getId(),
1764
                'name' => $inviteeUser->getCompleteNameWithUsername(),
1765
            ];
1766
        }
1767
1768
        return $inviteeList;
1769
    }
1770
1771
    /**
1772
     * Get user/group list per event.
1773
     *
1774
     * @param int $eventId
1775
     * @param int $courseId
1776
     * @param int $sessionId
1777
     * @paraù int $sessionId
1778
     *
1779
     * @return array
1780
     */
1781
    public function getUsersAndGroupSubscribedToEvent(
1782
        $eventId,
1783
        $courseId,
1784
        $sessionId
1785
    ) {
1786
        $eventId = (int) $eventId;
1787
        $courseId = (int) $courseId;
1788
        $sessionId = (int) $sessionId;
1789
1790
        $sessionCondition = "ip.session_id = $sessionId";
1791
        if (empty($sessionId)) {
1792
            $sessionCondition = " (ip.session_id = 0 OR ip.session_id IS NULL) ";
1793
        }
1794
1795
        $tlb_course_agenda = Database::get_course_table(TABLE_AGENDA);
1796
        $tbl_property = Database::get_course_table(TABLE_ITEM_PROPERTY);
1797
1798
        // Get sent_tos
1799
        $sql = "SELECT DISTINCT to_user_id, to_group_id
1800
                FROM $tbl_property ip
1801
                INNER JOIN $tlb_course_agenda agenda
1802
                ON (
1803
                  ip.ref = agenda.id AND
1804
                  ip.c_id = agenda.c_id AND
1805
                  ip.tool = '".TOOL_CALENDAR_EVENT."'
1806
                )
1807
                WHERE
1808
                    ref = $eventId AND
1809
                    ip.visibility = '1' AND
1810
                    ip.c_id = $courseId AND
1811
                    $sessionCondition
1812
                ";
1813
1814
        $result = Database::query($sql);
1815
        $users = [];
1816
        $groups = [];
1817
        $everyone = false;
1818
1819
        while ($row = Database::fetch_array($result, 'ASSOC')) {
1820
            if (!empty($row['to_group_id'])) {
1821
                $groups[] = $row['to_group_id'];
1822
            }
1823
            if (!empty($row['to_user_id'])) {
1824
                $users[] = $row['to_user_id'];
1825
            }
1826
1827
            if (empty($groups) && empty($users)) {
1828
                if ($row['to_group_id'] == 0) {
1829
                    $everyone = true;
1830
                }
1831
            }
1832
        }
1833
1834
        return [
1835
            'everyone' => $everyone,
1836
            'users' => $users,
1837
            'groups' => $groups,
1838
        ];
1839
    }
1840
1841
    /**
1842
     * @param int    $start
1843
     * @param int    $end
1844
     * @param int    $sessionId
1845
     * @param int    $userId
1846
     * @param string $color
1847
     *
1848
     * @return array
1849
     */
1850
    public function getSessionEvents(
1851
        $start,
1852
        $end,
1853
        $sessionId = 0,
1854
        $userId = 0,
1855
        $color = ''
1856
    ) {
1857
        $courses = SessionManager::get_course_list_by_session_id($sessionId);
1858
1859
        if (!empty($courses)) {
1860
            foreach ($courses as $course) {
1861
                $this->getCourseEvents(
1862
                    $start,
1863
                    $end,
1864
                    $course,
1865
                    0,
1866
                    $sessionId,
1867
                    0,
1868
                    $color
1869
                );
1870
            }
1871
        }
1872
    }
1873
1874
    /**
1875
     * @param int    $start
1876
     * @param int    $end
1877
     * @param array  $courseInfo
1878
     * @param int    $groupId
1879
     * @param int    $sessionId
1880
     * @param int    $user_id
1881
     * @param string $color
1882
     *
1883
     * @return array
1884
     */
1885
    public function getCourseEvents(
1886
        $start,
1887
        $end,
1888
        $courseInfo,
1889
        $groupId = 0,
1890
        $sessionId = 0,
1891
        $user_id = 0,
1892
        $color = ''
1893
    ) {
1894
        $start = isset($start) && !empty($start) ? api_get_utc_datetime(intval($start)) : null;
1895
        $end = isset($end) && !empty($end) ? api_get_utc_datetime(intval($end)) : null;
1896
1897
        if (empty($courseInfo)) {
1898
            return [];
1899
        }
1900
        $courseId = $courseInfo['real_id'];
1901
1902
        if (empty($courseId)) {
1903
            return [];
1904
        }
1905
1906
        $sessionId = (int) $sessionId;
1907
        $user_id = (int) $user_id;
1908
1909
        $groupList = GroupManager::get_group_list(
1910
            null,
1911
            $courseInfo,
1912
            null,
1913
            $sessionId
1914
        );
1915
1916
        $groupNameList = [];
1917
        if (!empty($groupList)) {
1918
            foreach ($groupList as $group) {
1919
                $groupNameList[$group['iid']] = $group['name'];
1920
            }
1921
        }
1922
1923
        if (api_is_platform_admin() || api_is_allowed_to_edit()) {
1924
            $isAllowToEdit = true;
1925
        } else {
1926
            $isAllowToEdit = CourseManager::is_course_teacher(
1927
                api_get_user_id(),
1928
                $courseInfo['code']
1929
            );
1930
        }
1931
1932
        $isAllowToEditByHrm = false;
1933
        if (!empty($sessionId)) {
1934
            $allowDhrToEdit = api_get_configuration_value('allow_agenda_edit_for_hrm');
1935
            if ($allowDhrToEdit) {
1936
                $isHrm = SessionManager::isUserSubscribedAsHRM($sessionId, api_get_user_id());
1937
                if ($isHrm) {
1938
                    $isAllowToEdit = $isAllowToEditByHrm = true;
1939
                }
1940
            }
1941
        }
1942
1943
        $groupMemberships = [];
1944
        if (!empty($groupId)) {
1945
            $groupMemberships = [$groupId];
1946
        } else {
1947
            if ($isAllowToEdit) {
1948
                if (!empty($groupList)) {
1949
                    // c_item_property.to_group_id field was migrated to use
1950
                    // c_group_info.iid
1951
                    $groupMemberships = array_column($groupList, 'iid');
1952
                }
1953
            } else {
1954
                // get only related groups from user
1955
                $groupMemberships = GroupManager::get_group_ids(
1956
                    $courseId,
1957
                    api_get_user_id()
1958
                );
1959
            }
1960
        }
1961
1962
        $tlb_course_agenda = Database::get_course_table(TABLE_AGENDA);
1963
        $tbl_property = Database::get_course_table(TABLE_ITEM_PROPERTY);
1964
1965
        $shareEventsInSessions = 1 == api_get_course_setting('agenda_share_events_in_sessions', $courseInfo);
1966
1967
        $agendaSessionCondition = str_replace(
1968
            ' AND ',
1969
            '',
1970
            api_get_session_condition($sessionId, true, $shareEventsInSessions, 'agenda.session_id')
1971
        );
1972
        $ipSessionCondition = api_get_session_condition($sessionId, true, $shareEventsInSessions, 'ip.session_id');
1973
1974
        $sessionCondition = "($agendaSessionCondition $ipSessionCondition)";
1975
1976
        if ($isAllowToEdit) {
1977
            // No group filter was asked
1978
            if (empty($groupId)) {
1979
                if (empty($user_id)) {
1980
                    // Show all events not added in group
1981
                    $userCondition = ' (ip.to_group_id IS NULL OR ip.to_group_id = 0) ';
1982
                    // admin see only his stuff
1983
                    if ($this->type === 'personal') {
1984
                        $userCondition = " (ip.to_user_id = ".api_get_user_id()." AND (ip.to_group_id IS NULL OR ip.to_group_id = 0) ) ";
1985
                        $userCondition .= " OR ( (ip.to_user_id = 0 OR ip.to_user_id is NULL)  AND (ip.to_group_id IS NULL OR ip.to_group_id = 0) ) ";
1986
                    }
1987
1988
                    if (!empty($groupMemberships)) {
1989
                        // Show events sent to selected groups
1990
                        $userCondition .= " OR (ip.to_user_id = 0 OR ip.to_user_id is NULL) AND (ip.to_group_id IN (".implode(", ", $groupMemberships).")) ";
1991
                    }
1992
                } else {
1993
                    // Show events of requested user in no group
1994
                    $userCondition = " (ip.to_user_id = $user_id AND (ip.to_group_id IS NULL OR ip.to_group_id = 0)) ";
1995
                    // Show events sent to selected groups
1996
                    if (!empty($groupMemberships)) {
1997
                        $userCondition .= " OR (ip.to_user_id = $user_id) AND (ip.to_group_id IN (".implode(", ", $groupMemberships).")) ";
1998
                    }
1999
                }
2000
            } else {
2001
                // Show only selected groups (depending of user status)
2002
                $userCondition = " (ip.to_user_id = 0 OR ip.to_user_id is NULL) AND (ip.to_group_id IN (".implode(", ", $groupMemberships).")) ";
2003
2004
                if (!empty($groupMemberships)) {
2005
                    // Show send to $user_id in selected groups
2006
                    $userCondition .= " OR (ip.to_user_id = $user_id) AND (ip.to_group_id IN (".implode(", ", $groupMemberships).")) ";
2007
                }
2008
            }
2009
        } else {
2010
            // No group filter was asked
2011
            if (empty($groupId)) {
2012
                // Show events sent to everyone and no group
2013
                $userCondition = ' ( (ip.to_user_id = 0 OR ip.to_user_id is NULL) AND (ip.to_group_id IS NULL OR ip.to_group_id = 0) ';
2014
2015
                // Show events sent to selected groups
2016
                if (!empty($groupMemberships)) {
2017
                    $userCondition .= " OR (ip.to_user_id = 0 OR ip.to_user_id is NULL) AND (ip.to_group_id IN (".implode(", ", $groupMemberships)."))) ";
2018
                } else {
2019
                    $userCondition .= " ) ";
2020
                }
2021
                $userCondition .= " OR (ip.to_user_id = ".api_get_user_id()." AND (ip.to_group_id IS NULL OR ip.to_group_id = 0)) ";
2022
            } else {
2023
                if (!empty($groupMemberships)) {
2024
                    // Show send to everyone - and only selected groups
2025
                    $userCondition = " (ip.to_user_id = 0 OR ip.to_user_id is NULL) AND (ip.to_group_id IN (".implode(", ", $groupMemberships).")) ";
2026
                }
2027
            }
2028
2029
            // Show sent to only me and no group
2030
            if (!empty($groupMemberships)) {
2031
                $userCondition .= " OR (ip.to_user_id = ".api_get_user_id().") AND (ip.to_group_id IN (".implode(", ", $groupMemberships).")) ";
2032
            } else {
2033
                // Show sent to only me and selected groups
2034
            }
2035
        }
2036
2037
        if (api_is_allowed_to_edit()) {
2038
            $visibilityCondition = " (ip.visibility IN ('1', '0'))  ";
2039
        } else {
2040
            $visibilityCondition = " (ip.visibility = '1') ";
2041
        }
2042
2043
        $sql = "SELECT DISTINCT
2044
                    agenda.*,
2045
                    ip.visibility,
2046
                    ip.to_group_id,
2047
                    ip.insert_user_id,
2048
                    ip.ref,
2049
                    to_user_id
2050
                FROM $tlb_course_agenda agenda
2051
                INNER JOIN $tbl_property ip
2052
                ON (
2053
                    agenda.id = ip.ref AND
2054
                    agenda.c_id = ip.c_id AND
2055
                    ip.tool = '".TOOL_CALENDAR_EVENT."'
2056
                )
2057
                WHERE
2058
                    $sessionCondition AND
2059
                    ($userCondition) AND
2060
                    $visibilityCondition AND
2061
                    agenda.c_id = $courseId
2062
        ";
2063
        $dateCondition = '';
2064
        if (!empty($start) && !empty($end)) {
2065
            $dateCondition .= "AND (
2066
                 agenda.start_date BETWEEN '".$start."' AND '".$end."' OR
2067
                 agenda.end_date BETWEEN '".$start."' AND '".$end."' OR
2068
                 (
2069
                     agenda.start_date IS NOT NULL AND agenda.end_date IS NOT NULL AND
2070
                     YEAR(agenda.start_date) = YEAR(agenda.end_date) AND
2071
                     MONTH('$start') BETWEEN MONTH(agenda.start_date) AND MONTH(agenda.end_date)
2072
                 )
2073
            )";
2074
        }
2075
2076
        $sql .= $dateCondition;
2077
        $result = Database::query($sql);
2078
2079
        $coachCanEdit = false;
2080
        if (!empty($sessionId)) {
2081
            $coachCanEdit = api_is_coach($sessionId, $courseId) || api_is_platform_admin();
2082
        }
2083
2084
        if (Database::num_rows($result)) {
2085
            $eventsAdded = array_column($this->events, 'unique_id');
2086
            while ($row = Database::fetch_array($result, 'ASSOC')) {
2087
                $event = [];
2088
                $event['id'] = 'course_'.$row['id'];
2089
                $event['unique_id'] = $row['iid'];
2090
                // To avoid doubles
2091
                if (in_array($event['unique_id'], $eventsAdded)) {
2092
                    continue;
2093
                }
2094
2095
                $eventsAdded[] = $event['unique_id'];
2096
                $eventId = $row['ref'];
2097
                $items = $this->getUsersAndGroupSubscribedToEvent(
2098
                    $eventId,
2099
                    $courseId,
2100
                    $this->sessionId
2101
                );
2102
                $group_to_array = $items['groups'];
2103
                $user_to_array = $items['users'];
2104
                $attachmentList = $this->getAttachmentList(
2105
                    $row['id'],
2106
                    $courseInfo
2107
                );
2108
                $event['attachment'] = '';
2109
                if (!empty($attachmentList)) {
2110
                    foreach ($attachmentList as $attachment) {
2111
                        $has_attachment = Display::return_icon(
2112
                            'attachment.gif',
2113
                            get_lang('Attachment')
2114
                        );
2115
                        $user_filename = $attachment['filename'];
2116
                        $url = api_get_path(WEB_CODE_PATH).'calendar/download.php?file='.$attachment['path'].'&course_id='.$courseId.'&'.api_get_cidreq();
2117
                        $event['attachment'] .= $has_attachment.
2118
                            Display::url(
2119
                                $user_filename,
2120
                                $url
2121
                            ).'<br />';
2122
                    }
2123
                }
2124
2125
                $event['title'] = $row['title'];
2126
                $event['className'] = 'course';
2127
                $event['allDay'] = 'false';
2128
                $event['course_id'] = $courseId;
2129
                $event['borderColor'] = $event['backgroundColor'] = $this->event_course_color;
2130
2131
                $sessionInfo = [];
2132
                if (isset($row['session_id']) && !empty($row['session_id'])) {
2133
                    $sessionInfo = api_get_session_info($sessionId);
2134
                    $event['borderColor'] = $event['backgroundColor'] = $this->event_session_color;
2135
                }
2136
2137
                $event['session_name'] = isset($sessionInfo['name']) ? $sessionInfo['name'] : '';
2138
                $event['course_name'] = isset($courseInfo['title']) ? $courseInfo['title'] : '';
2139
2140
                if (isset($row['to_group_id']) && !empty($row['to_group_id'])) {
2141
                    $event['borderColor'] = $event['backgroundColor'] = $this->event_group_color;
2142
                }
2143
2144
                if (!empty($color)) {
2145
                    $event['borderColor'] = $event['backgroundColor'] = $color;
2146
                }
2147
2148
                if (isset($row['color']) && !empty($row['color'])) {
2149
                    $event['borderColor'] = $event['backgroundColor'] = $row['color'];
2150
                }
2151
2152
                $event['editable'] = false;
2153
                if ($this->getIsAllowedToEdit() && $this->type == 'course') {
2154
                    $event['editable'] = true;
2155
                    if (!empty($sessionId)) {
2156
                        if ($coachCanEdit == false) {
2157
                            $event['editable'] = false;
2158
                        }
2159
                        if ($isAllowToEditByHrm) {
2160
                            $event['editable'] = true;
2161
                        }
2162
                        if ($sessionId != $row['session_id']) {
2163
                            $event['editable'] = false;
2164
                        }
2165
                    }
2166
                    // if user is author then he can edit the item
2167
                    if (api_get_user_id() == $row['insert_user_id']) {
2168
                        $event['editable'] = true;
2169
                    }
2170
                }
2171
2172
                if (!empty($row['start_date'])) {
2173
                    $event['start'] = $this->formatEventDate($row['start_date']);
2174
                    $event['start_date_localtime'] = api_get_local_time($row['start_date']);
2175
                }
2176
                if (!empty($row['end_date'])) {
2177
                    $event['end'] = $this->formatEventDate($row['end_date']);
2178
                    $event['end_date_localtime'] = api_get_local_time($row['end_date']);
2179
                }
2180
2181
                $event['sent_to'] = '';
2182
                $event['type'] = 'course';
2183
                if ($row['session_id'] != 0) {
2184
                    $event['type'] = 'session';
2185
                }
2186
2187
                // Event Sent to a group?
2188
                if (isset($row['to_group_id']) && !empty($row['to_group_id'])) {
2189
                    $sent_to = [];
2190
                    if (!empty($group_to_array)) {
2191
                        foreach ($group_to_array as $group_item) {
2192
                            $sent_to[] = $groupNameList[$group_item];
2193
                        }
2194
                    }
2195
                    $sent_to = implode('@@', $sent_to);
2196
                    $sent_to = str_replace(
2197
                        '@@',
2198
                        '</div><div class="label_tag notice">',
2199
                        $sent_to
2200
                    );
2201
                    $event['sent_to'] = '<div class="label_tag notice">'.$sent_to.'</div>';
2202
                    $event['type'] = 'group';
2203
                }
2204
2205
                // Event sent to a user?
2206
                if (isset($row['to_user_id'])) {
2207
                    $sent_to = [];
2208
                    if (!empty($user_to_array)) {
2209
                        foreach ($user_to_array as $item) {
2210
                            $user_info = api_get_user_info($item);
2211
                            // Add username as tooltip for $event['sent_to'] - ref #4226
2212
                            $username = api_htmlentities(
2213
                                sprintf(
2214
                                    get_lang('LoginX'),
2215
                                    $user_info['username']
2216
                                ),
2217
                                ENT_QUOTES
2218
                            );
2219
                            $sent_to[] = "<span title='".$username."'>".$user_info['complete_name']."</span>";
2220
                        }
2221
                    }
2222
                    $sent_to = implode('@@', $sent_to);
2223
                    $sent_to = str_replace(
2224
                        '@@',
2225
                        '</div><div class="label_tag notice">',
2226
                        $sent_to
2227
                    );
2228
                    $event['sent_to'] = '<div class="label_tag notice">'.$sent_to.'</div>';
2229
                }
2230
2231
                //Event sent to everyone!
2232
                if (empty($event['sent_to'])) {
2233
                    $event['sent_to'] = '<div class="label_tag notice">'.get_lang('Everyone').'</div>';
2234
                }
2235
2236
                $event['description'] = Security::remove_XSS($row['content']);
2237
                $event['visibility'] = $row['visibility'];
2238
                $event['real_id'] = $row['id'];
2239
                $event['allDay'] = isset($row['all_day']) && $row['all_day'] == 1 ? $row['all_day'] : 0;
2240
                $event['parent_event_id'] = $row['parent_event_id'];
2241
                $event['has_children'] = $this->hasChildren($row['id'], $courseId) ? 1 : 0;
2242
                $event['comment'] = Security::remove_XSS($row['comment']);
2243
                $this->events[] = $event;
2244
            }
2245
        }
2246
2247
        return $this->events;
2248
    }
2249
2250
    /**
2251
     * @param int $start tms
2252
     * @param int $end   tms
2253
     *
2254
     * @return array
2255
     */
2256
    public function getPlatformEvents($start, $end)
2257
    {
2258
        $start = isset($start) && !empty($start) ? api_get_utc_datetime(intval($start)) : null;
2259
        $end = isset($end) && !empty($end) ? api_get_utc_datetime(intval($end)) : null;
2260
        $dateCondition = '';
2261
2262
        if (!empty($start) && !empty($end)) {
2263
            $dateCondition .= "AND (
2264
                 start_date BETWEEN '".$start."' AND '".$end."' OR
2265
                 end_date BETWEEN '".$start."' AND '".$end."' OR
2266
                 (
2267
                     start_date IS NOT NULL AND end_date IS NOT NULL AND
2268
                     YEAR(start_date) = YEAR(end_date) AND
2269
                     MONTH('$start') BETWEEN MONTH(start_date) AND MONTH(end_date)
2270
                 )
2271
            )";
2272
        }
2273
2274
        $access_url_id = api_get_current_access_url_id();
2275
2276
        $sql = "SELECT *
2277
                FROM ".$this->tbl_global_agenda."
2278
                WHERE access_url_id = $access_url_id
2279
                $dateCondition";
2280
        $result = Database::query($sql);
2281
        $my_events = [];
2282
        if (Database::num_rows($result)) {
2283
            while ($row = Database::fetch_array($result, 'ASSOC')) {
2284
                $event = [];
2285
                $event['id'] = 'platform_'.$row['id'];
2286
                $event['title'] = $row['title'];
2287
                $event['className'] = 'platform';
2288
                $event['allDay'] = 'false';
2289
                $event['borderColor'] = $event['backgroundColor'] = $this->event_platform_color;
2290
                $event['editable'] = false;
2291
                $event['type'] = 'admin';
2292
2293
                if (api_is_platform_admin() && $this->type === 'admin') {
2294
                    $event['editable'] = true;
2295
                }
2296
2297
                if (!empty($row['start_date'])) {
2298
                    $event['start'] = $this->formatEventDate($row['start_date']);
2299
                    $event['start_date_localtime'] = api_get_local_time($row['start_date']);
2300
                }
2301
2302
                if (!empty($row['end_date'])) {
2303
                    $event['end'] = $this->formatEventDate($row['end_date']);
2304
                    $event['end_date_localtime'] = api_get_local_time($row['end_date']);
2305
                }
2306
                $event['allDay'] = isset($row['all_day']) && $row['all_day'] == 1 ? $row['all_day'] : 0;
2307
                $event['parent_event_id'] = 0;
2308
                $event['has_children'] = 0;
2309
                $event['description'] = $row['content'];
2310
2311
                $my_events[] = $event;
2312
                $this->events[] = $event;
2313
            }
2314
        }
2315
2316
        return $my_events;
2317
    }
2318
2319
    /**
2320
     * @param FormValidator $form
2321
     * @param array         $groupList
2322
     * @param array         $userList
2323
     * @param array         $sendTo               array('users' => [1, 2], 'groups' => [3, 4])
2324
     * @param array         $attributes
2325
     * @param bool          $addOnlyItemsInSendTo
2326
     * @param bool          $required
2327
     */
2328
    public function setSendToSelect(
2329
        $form,
2330
        $groupList = [],
2331
        $userList = [],
2332
        $sendTo = [],
2333
        $attributes = [],
2334
        $addOnlyItemsInSendTo = false,
2335
        $required = false
2336
    ) {
2337
        $params = [
2338
            'id' => 'users_to_send_id',
2339
            'data-placeholder' => get_lang('Select'),
2340
            'multiple' => 'multiple',
2341
            'class' => 'multiple-select',
2342
        ];
2343
2344
        if (!empty($attributes)) {
2345
            $params = array_merge($params, $attributes);
2346
            if (empty($params['multiple'])) {
2347
                unset($params['multiple']);
2348
            }
2349
        }
2350
2351
        $sendToGroups = isset($sendTo['groups']) ? $sendTo['groups'] : [];
2352
        $sendToUsers = isset($sendTo['users']) ? $sendTo['users'] : [];
2353
2354
        /** @var HTML_QuickForm_select $select */
2355
        $select = $form->addSelect(
2356
            'users_to_send',
2357
            get_lang('To'),
2358
            null,
2359
            $params
2360
        );
2361
2362
        if ($required) {
2363
            $form->setRequired($select);
2364
        }
2365
2366
        $selectedEveryoneOptions = [];
2367
        if (isset($sendTo['everyone']) && $sendTo['everyone']) {
2368
            $selectedEveryoneOptions = ['selected'];
2369
            $sendToUsers = [];
2370
        }
2371
2372
        $select->addOption(
2373
            get_lang('Everyone'),
2374
            'everyone',
2375
            $selectedEveryoneOptions
2376
        );
2377
2378
        $options = [];
2379
        if (is_array($groupList)) {
2380
            foreach ($groupList as $group) {
2381
                $count_users = isset($group['count_users']) ? $group['count_users'] : $group['userNb'];
2382
                $count_users = " &ndash; $count_users ".get_lang('Users');
2383
                $option = [
2384
                    'text' => $group['name'].$count_users,
2385
                    'value' => "GROUP:".$group['id'],
2386
                ];
2387
                $selected = in_array(
2388
                    $group['id'],
2389
                    $sendToGroups
2390
                ) ? true : false;
2391
                if ($selected) {
2392
                    $option['selected'] = 'selected';
2393
                }
2394
2395
                if ($addOnlyItemsInSendTo) {
2396
                    if ($selected) {
2397
                        $options[] = $option;
2398
                    }
2399
                } else {
2400
                    $options[] = $option;
2401
                }
2402
            }
2403
            $select->addOptGroup($options, get_lang('Groups'));
2404
        }
2405
2406
        // adding the individual users to the select form
2407
        if (is_array($userList)) {
2408
            $options = [];
2409
            foreach ($userList as $user) {
2410
                if ($user['status'] == ANONYMOUS) {
2411
                    continue;
2412
                }
2413
                $option = [
2414
                    'text' => api_get_person_name(
2415
                            $user['firstname'],
2416
                            $user['lastname']
2417
                        ).' ('.$user['username'].')',
2418
                    'value' => "USER:".$user['user_id'],
2419
                ];
2420
2421
                $selected = in_array(
2422
                    $user['user_id'],
2423
                    $sendToUsers
2424
                ) ? true : false;
2425
2426
                if ($selected) {
2427
                    $option['selected'] = 'selected';
2428
                }
2429
2430
                if ($addOnlyItemsInSendTo) {
2431
                    if ($selected) {
2432
                        $options[] = $option;
2433
                    }
2434
                } else {
2435
                    $options[] = $option;
2436
                }
2437
            }
2438
2439
            $select->addOptGroup($options, get_lang('Users'));
2440
        }
2441
    }
2442
2443
    /**
2444
     * Separates the users and groups array
2445
     * users have a value USER:XXX (with XXX the user id
2446
     * groups have a value GROUP:YYY (with YYY the group id)
2447
     * use the 'everyone' key.
2448
     *
2449
     * @author Julio Montoya based in separate_users_groups in agenda.inc.php
2450
     *
2451
     * @param array $to
2452
     *
2453
     * @return array
2454
     */
2455
    public function parseSendToArray($to)
2456
    {
2457
        $groupList = [];
2458
        $userList = [];
2459
        $sendTo = null;
2460
2461
        $sendTo['everyone'] = false;
2462
        if (is_array($to) && count($to) > 0) {
2463
            foreach ($to as $item) {
2464
                if ($item == 'everyone') {
2465
                    $sendTo['everyone'] = true;
2466
                } else {
2467
                    list($type, $id) = explode(':', $item);
2468
                    switch ($type) {
2469
                        case 'GROUP':
2470
                            $groupList[] = $id;
2471
                            break;
2472
                        case 'USER':
2473
                            $userList[] = $id;
2474
                            break;
2475
                    }
2476
                }
2477
            }
2478
            $sendTo['groups'] = $groupList;
2479
            $sendTo['users'] = $userList;
2480
        }
2481
2482
        return $sendTo;
2483
    }
2484
2485
    /**
2486
     * @param array $params
2487
     *
2488
     * @return FormValidator
2489
     */
2490
    public function getForm($params = [])
2491
    {
2492
        $action = isset($params['action']) ? Security::remove_XSS($params['action']) : null;
2493
        $id = isset($params['id']) ? (int) $params['id'] : 0;
2494
2495
        $url = api_get_self().'?action='.$action.'&id='.$id.'&type='.$this->type;
2496
        if ($this->type == 'course') {
2497
            $url = api_get_self().'?'.api_get_cidreq().'&action='.$action.'&id='.$id.'&type='.$this->type;
2498
        }
2499
2500
        $form = new FormValidator(
2501
            'add_event',
2502
            'post',
2503
            $url,
2504
            null,
2505
            ['enctype' => 'multipart/form-data']
2506
        );
2507
2508
        $idAttach = isset($params['id_attach']) ? (int) $params['id_attach'] : null;
2509
        $groupId = api_get_group_id();
2510
        $form_Title = get_lang('AddCalendarItem');
2511
        if (!empty($id)) {
2512
            $form_Title = get_lang('ModifyCalendarItem');
2513
        }
2514
2515
        $form->addHeader($form_Title);
2516
        $form->addElement('hidden', 'id', $id);
2517
        $form->addElement('hidden', 'action', $action);
2518
        $form->addElement('hidden', 'id_attach', $idAttach);
2519
2520
        $isSubEventEdition = false;
2521
        $isParentFromSerie = false;
2522
        $showAttachmentForm = true;
2523
2524
        if ($this->type == 'course') {
2525
            // Edition mode.
2526
            if (!empty($id)) {
2527
                $showAttachmentForm = false;
2528
                if (isset($params['parent_event_id']) && !empty($params['parent_event_id'])) {
2529
                    $isSubEventEdition = true;
2530
                }
2531
                if (!empty($params['repeat_info'])) {
2532
                    $isParentFromSerie = true;
2533
                }
2534
            }
2535
        }
2536
2537
        if ($isSubEventEdition) {
2538
            $form->addElement(
2539
                'label',
2540
                null,
2541
                Display::return_message(
2542
                    get_lang('EditingThisEventWillRemoveItFromTheSerie'),
2543
                    'warning'
2544
                )
2545
            );
2546
        }
2547
2548
        $form->addElement('text', 'title', get_lang('ItemTitle'));
2549
2550
        if (isset($groupId) && !empty($groupId)) {
2551
            $form->addElement(
2552
                'hidden',
2553
                'users_to_send[]',
2554
                "GROUP:$groupId"
2555
            );
2556
            $form->addElement('hidden', 'to', 'true');
2557
        } else {
2558
            $sendTo = isset($params['send_to']) ? $params['send_to'] : ['everyone' => true];
2559
            if ($this->type == 'course') {
2560
                $this->showToForm($form, $sendTo, [], false, true);
2561
            }
2562
        }
2563
2564
        $form->addDateRangePicker(
2565
            'date_range',
2566
            get_lang('DateRange'),
2567
            false,
2568
            ['id' => 'date_range']
2569
        );
2570
        $form->addElement('checkbox', 'all_day', null, get_lang('AllDay'));
2571
2572
        if ($this->type == 'course') {
2573
            $repeat = $form->addElement(
2574
                'checkbox',
2575
                'repeat',
2576
                null,
2577
                get_lang('RepeatEvent'),
2578
                ['onclick' => 'return plus_repeated_event();']
2579
            );
2580
            $form->addElement(
2581
                'html',
2582
                '<div id="options2" style="display:none">'
2583
            );
2584
            $form->addElement(
2585
                'select',
2586
                'repeat_type',
2587
                get_lang('RepeatType'),
2588
                self::getRepeatTypes()
2589
            );
2590
            $form->addElement(
2591
                'date_picker',
2592
                'repeat_end_day',
2593
                get_lang('RepeatEnd'),
2594
                ['id' => 'repeat_end_date_form']
2595
            );
2596
2597
            if ($isSubEventEdition || $isParentFromSerie) {
2598
                $repeatInfo = $params['repeat_info'];
2599
                if ($isSubEventEdition) {
2600
                    $parentEvent = $params['parent_info'];
2601
                    $repeatInfo = $parentEvent['repeat_info'];
2602
                }
2603
                $params['repeat'] = 1;
2604
                $params['repeat_type'] = $repeatInfo['cal_type'];
2605
                $params['repeat_end_day'] = substr(
2606
                    api_get_local_time($repeatInfo['cal_end']),
2607
                    0,
2608
                    10
2609
                );
2610
2611
                $form->freeze(['repeat_type', 'repeat_end_day']);
2612
                $repeat->_attributes['disabled'] = 'disabled';
2613
            }
2614
            $form->addElement('html', '</div>');
2615
        }
2616
2617
        if (!empty($id)) {
2618
            if (empty($params['end_date'])) {
2619
                $params['date_range'] = $params['end_date'];
2620
            }
2621
2622
            $params['date_range'] =
2623
                substr(api_get_local_time($params['start_date']), 0, 16).' / '.
2624
                substr(api_get_local_time($params['end_date']), 0, 16);
2625
        }
2626
2627
        $toolbar = 'Agenda';
2628
        if (!api_is_allowed_to_edit(null, true)) {
2629
            $toolbar = 'AgendaStudent';
2630
        }
2631
2632
        $form->addElement(
2633
            'html_editor',
2634
            'content',
2635
            get_lang('Description'),
2636
            null,
2637
            [
2638
                'ToolbarSet' => $toolbar,
2639
                'Width' => '100%',
2640
                'Height' => '200',
2641
            ]
2642
        );
2643
2644
        if ($this->type == 'course') {
2645
            $form->addElement('textarea', 'comment', get_lang('Comment'));
2646
            $form->addLabel(
2647
                get_lang('FilesAttachment'),
2648
                '<div id="filepaths" class="file-upload-event">
2649
2650
                        <div id="filepath_1">
2651
                            <input type="file" name="attach_1"/>
2652
2653
                            <label>'.get_lang('Description').'</label>
2654
                            <input class="form-control" type="text" name="legend[]" />
2655
                        </div>
2656
2657
                    </div>'
2658
            );
2659
2660
            $form->addLabel(
2661
                '',
2662
                '<span id="link-more-attach">
2663
                    <a href="javascript://" onclick="return add_image_form()">'.
2664
                get_lang('AddOneMoreFile').'</a>
2665
                 </span>&nbsp;('.sprintf(
2666
                    get_lang('MaximunFileSizeX'),
2667
                    format_file_size(
2668
                        api_get_setting('message_max_upload_filesize')
2669
                    )
2670
                ).')'
2671
            );
2672
2673
            if (isset($params['attachment']) && !empty($params['attachment'])) {
2674
                $attachmentList = $params['attachment'];
2675
                foreach ($attachmentList as $attachment) {
2676
                    $params['file_comment'] = $attachment['comment'];
2677
                    if (!empty($attachment['path'])) {
2678
                        $form->addElement(
2679
                            'checkbox',
2680
                            'delete_attachment['.$attachment['id'].']',
2681
                            null,
2682
                            get_lang(
2683
                                'DeleteAttachment'
2684
                            ).': '.$attachment['filename']
2685
                        );
2686
                    }
2687
                }
2688
            }
2689
2690
            $form->addElement(
2691
                'textarea',
2692
                'file_comment',
2693
                get_lang('FileComment')
2694
            );
2695
        }
2696
2697
        if (empty($id) && 'course' === $this->type) {
2698
            $form->addElement(
2699
                'checkbox',
2700
                'add_announcement',
2701
                null,
2702
                get_lang('AddAnnouncement').'&nbsp('.get_lang('SendMail').')'
2703
            );
2704
        }
2705
2706
        $agendaCollectiveInvitations = api_get_configuration_value('agenda_collective_invitations');
2707
2708
        if ($agendaCollectiveInvitations && 'personal' === $this->type) {
2709
            $em = Database::getManager();
2710
2711
            $invitees = [];
2712
            $isCollective = false;
2713
2714
            if ($id) {
2715
                $event = $em->find('ChamiloCoreBundle:PersonalAgenda', $id);
2716
                $eventInvitation = $event->getInvitation();
2717
2718
                if ($eventInvitation) {
2719
                    foreach ($eventInvitation->getInvitees() as $invitee) {
2720
                        $inviteeUser = $invitee->getUser();
2721
2722
                        $invitees[$inviteeUser->getId()] = $inviteeUser->getCompleteNameWithUsername();
2723
                    }
2724
                }
2725
2726
                $isCollective = $event->isCollective();
2727
            }
2728
2729
            $form->addSelectAjax(
2730
                'invitees',
2731
                get_lang('Invitees'),
2732
                $invitees,
2733
                [
2734
                    'multiple' => 'multiple',
2735
                    'url' => api_get_path(WEB_AJAX_PATH).'message.ajax.php?a=find_users',
2736
                ]
2737
            );
2738
            $form->addCheckBox('collective', '', get_lang('IsItEditableByTheInvitees'));
2739
2740
            $params['invitees'] = array_keys($invitees);
2741
            $params['collective'] = $isCollective;
2742
        }
2743
2744
        if (api_get_configuration_value('agenda_reminders') && 'add' === $params['action']) {
2745
            $form->addHtml('<hr><div id="notification_list"></div>');
2746
            $form->addButton('add_notification', get_lang('AddNotification'), 'bell-o')->setType('button');
2747
        }
2748
2749
        if ($id) {
2750
            $form->addButtonUpdate(get_lang('ModifyEvent'));
2751
        } else {
2752
            $form->addButtonSave(get_lang('AgendaAdd'));
2753
        }
2754
2755
        $form->setDefaults($params);
2756
        $form->addRule(
2757
            'date_range',
2758
            get_lang('ThisFieldIsRequired'),
2759
            'required'
2760
        );
2761
        $form->addRule('title', get_lang('ThisFieldIsRequired'), 'required');
2762
2763
        return $form;
2764
    }
2765
2766
    /**
2767
     * @param FormValidator $form
2768
     * @param array         $sendTo               array('everyone' => false, 'users' => [1, 2], 'groups' => [3, 4])
2769
     * @param array         $attributes
2770
     * @param bool          $addOnlyItemsInSendTo
2771
     * @param bool          $required
2772
     *
2773
     * @return bool
2774
     */
2775
    public function showToForm(
2776
        $form,
2777
        $sendTo = [],
2778
        $attributes = [],
2779
        $addOnlyItemsInSendTo = false,
2780
        $required = false
2781
    ) {
2782
        if ($this->type != 'course') {
2783
            return false;
2784
        }
2785
2786
        $order = 'lastname';
2787
        if (api_is_western_name_order()) {
2788
            $order = 'firstname';
2789
        }
2790
2791
        $userList = CourseManager::get_user_list_from_course_code(
2792
            api_get_course_id(),
2793
            $this->sessionId,
2794
            null,
2795
            $order
2796
        );
2797
2798
        $groupList = CourseManager::get_group_list_of_course(
2799
            api_get_course_id(),
2800
            $this->sessionId
2801
        );
2802
2803
        $this->setSendToSelect(
2804
            $form,
2805
            $groupList,
2806
            $userList,
2807
            $sendTo,
2808
            $attributes,
2809
            $addOnlyItemsInSendTo,
2810
            $required
2811
        );
2812
2813
        return true;
2814
    }
2815
2816
    /**
2817
     * @param int   $id
2818
     * @param int   $visibility 0= invisible, 1 visible
2819
     * @param array $courseInfo
2820
     * @param int   $userId
2821
     */
2822
    public static function changeVisibility(
2823
        $id,
2824
        $visibility,
2825
        $courseInfo,
2826
        $userId = null
2827
    ) {
2828
        $id = intval($id);
2829
        if (empty($userId)) {
2830
            $userId = api_get_user_id();
2831
        } else {
2832
            $userId = intval($userId);
2833
        }
2834
2835
        if ($visibility == 0) {
2836
            api_item_property_update(
2837
                $courseInfo,
2838
                TOOL_CALENDAR_EVENT,
2839
                $id,
2840
                'invisible',
2841
                $userId
2842
            );
2843
        } else {
2844
            api_item_property_update(
2845
                $courseInfo,
2846
                TOOL_CALENDAR_EVENT,
2847
                $id,
2848
                'visible',
2849
                $userId
2850
            );
2851
        }
2852
    }
2853
2854
    /**
2855
     * Get repeat types.
2856
     *
2857
     * @return array
2858
     */
2859
    public static function getRepeatTypes()
2860
    {
2861
        return [
2862
            'daily' => get_lang('RepeatDaily'),
2863
            'weekly' => get_lang('RepeatWeekly'),
2864
            'monthlyByDate' => get_lang('RepeatMonthlyByDate'),
2865
            //monthlyByDay"> get_lang('RepeatMonthlyByDay');
2866
            //monthlyByDayR' => get_lang('RepeatMonthlyByDayR'),
2867
            'yearly' => get_lang('RepeatYearly'),
2868
        ];
2869
    }
2870
2871
    /**
2872
     * Show a list with all the attachments according to the post's id.
2873
     *
2874
     * @param int   $eventId
2875
     * @param array $courseInfo
2876
     *
2877
     * @return array with the post info
2878
     */
2879
    public function getAttachmentList($eventId, $courseInfo)
2880
    {
2881
        $tableAttachment = Database::get_course_table(TABLE_AGENDA_ATTACHMENT);
2882
        $courseId = (int) $courseInfo['real_id'];
2883
        $eventId = (int) $eventId;
2884
2885
        $sql = "SELECT id, path, filename, comment
2886
                FROM $tableAttachment
2887
                WHERE
2888
                    c_id = $courseId AND
2889
                    agenda_id = $eventId";
2890
        $result = Database::query($sql);
2891
        $list = [];
2892
        if (Database::num_rows($result) != 0) {
2893
            $list = Database::store_result($result, 'ASSOC');
2894
        }
2895
2896
        return $list;
2897
    }
2898
2899
    /**
2900
     * Show a list with all the attachments according to the post's id.
2901
     *
2902
     * @param int   $attachmentId
2903
     * @param int   $eventId
2904
     * @param array $courseInfo
2905
     *
2906
     * @return array with the post info
2907
     */
2908
    public function getAttachment($attachmentId, $eventId, $courseInfo)
2909
    {
2910
        if (empty($courseInfo) || empty($attachmentId) || empty($eventId)) {
2911
            return [];
2912
        }
2913
2914
        $tableAttachment = Database::get_course_table(TABLE_AGENDA_ATTACHMENT);
2915
        $courseId = (int) $courseInfo['real_id'];
2916
        $eventId = (int) $eventId;
2917
        $attachmentId = (int) $attachmentId;
2918
2919
        $row = [];
2920
        $sql = "SELECT id, path, filename, comment
2921
                FROM $tableAttachment
2922
                WHERE
2923
                    c_id = $courseId AND
2924
                    agenda_id = $eventId AND
2925
                    id = $attachmentId
2926
                ";
2927
        $result = Database::query($sql);
2928
        if (Database::num_rows($result) != 0) {
2929
            $row = Database::fetch_array($result, 'ASSOC');
2930
        }
2931
2932
        return $row;
2933
    }
2934
2935
    /**
2936
     * Add an attachment file into agenda.
2937
     *
2938
     * @param int    $eventId
2939
     * @param array  $fileUserUpload ($_FILES['user_upload'])
2940
     * @param string $comment        about file
2941
     * @param array  $courseInfo
2942
     *
2943
     * @return string
2944
     */
2945
    public function addAttachment(
2946
        $eventId,
2947
        $fileUserUpload,
2948
        $comment,
2949
        $courseInfo
2950
    ) {
2951
        $agenda_table_attachment = Database::get_course_table(TABLE_AGENDA_ATTACHMENT);
2952
        $eventId = (int) $eventId;
2953
2954
        // Storing the attachments
2955
        $upload_ok = false;
2956
        if (!empty($fileUserUpload['name'])) {
2957
            $upload_ok = process_uploaded_file($fileUserUpload);
2958
        }
2959
2960
        if (!empty($upload_ok)) {
2961
            $courseDir = $courseInfo['directory'].'/upload/calendar';
2962
            $sys_course_path = api_get_path(SYS_COURSE_PATH);
2963
            $uploadDir = $sys_course_path.$courseDir;
2964
2965
            // Try to add an extension to the file if it hasn't one
2966
            $new_file_name = add_ext_on_mime(
2967
                stripslashes($fileUserUpload['name']),
2968
                $fileUserUpload['type']
2969
            );
2970
2971
            // user's file name
2972
            $file_name = $fileUserUpload['name'];
2973
2974
            if (!filter_extension($new_file_name)) {
2975
                return Display::return_message(
2976
                    get_lang('UplUnableToSaveFileFilteredExtension'),
2977
                    'error'
2978
                );
2979
            } else {
2980
                $new_file_name = uniqid('');
2981
                $new_path = $uploadDir.'/'.$new_file_name;
2982
                $result = @move_uploaded_file(
2983
                    $fileUserUpload['tmp_name'],
2984
                    $new_path
2985
                );
2986
                $courseId = api_get_course_int_id();
2987
                $size = intval($fileUserUpload['size']);
2988
                // Storing the attachments if any
2989
                if ($result) {
2990
                    $params = [
2991
                        'c_id' => $courseId,
2992
                        'filename' => $file_name,
2993
                        'comment' => $comment,
2994
                        'path' => $new_file_name,
2995
                        'agenda_id' => $eventId,
2996
                        'size' => $size,
2997
                    ];
2998
                    $id = Database::insert($agenda_table_attachment, $params);
2999
                    if ($id) {
3000
                        $sql = "UPDATE $agenda_table_attachment
3001
                                SET id = iid WHERE iid = $id";
3002
                        Database::query($sql);
3003
3004
                        api_item_property_update(
3005
                            $courseInfo,
3006
                            'calendar_event_attachment',
3007
                            $id,
3008
                            'AgendaAttachmentAdded',
3009
                            api_get_user_id()
3010
                        );
3011
                    }
3012
                }
3013
            }
3014
        }
3015
    }
3016
3017
    /**
3018
     * @param int    $attachmentId
3019
     * @param int    $eventId
3020
     * @param array  $fileUserUpload
3021
     * @param string $comment
3022
     * @param array  $courseInfo
3023
     */
3024
    public function updateAttachment(
3025
        $attachmentId,
3026
        $eventId,
3027
        $fileUserUpload,
3028
        $comment,
3029
        $courseInfo
3030
    ) {
3031
        $attachment = $this->getAttachment(
3032
            $attachmentId,
3033
            $eventId,
3034
            $courseInfo
3035
        );
3036
        if (!empty($attachment)) {
3037
            $this->deleteAttachmentFile($attachmentId, $courseInfo);
3038
        }
3039
        $this->addAttachment($eventId, $fileUserUpload, $comment, $courseInfo);
3040
    }
3041
3042
    /**
3043
     * This function delete a attachment file by id.
3044
     *
3045
     * @param int   $attachmentId
3046
     * @param array $courseInfo
3047
     *
3048
     * @return string
3049
     */
3050
    public function deleteAttachmentFile($attachmentId, $courseInfo)
3051
    {
3052
        $table = Database::get_course_table(TABLE_AGENDA_ATTACHMENT);
3053
        $attachmentId = (int) $attachmentId;
3054
        $courseId = $courseInfo['real_id'];
3055
3056
        if (empty($courseId) || empty($attachmentId)) {
3057
            return false;
3058
        }
3059
3060
        $sql = "DELETE FROM $table
3061
                WHERE c_id = $courseId AND id = ".$attachmentId;
3062
        $result = Database::query($sql);
3063
3064
        // update item_property
3065
        api_item_property_update(
3066
            $courseInfo,
3067
            'calendar_event_attachment',
3068
            $attachmentId,
3069
            'AgendaAttachmentDeleted',
3070
            api_get_user_id()
3071
        );
3072
3073
        if (!empty($result)) {
3074
            return Display::return_message(
3075
                get_lang("AttachmentFileDeleteSuccess"),
3076
                'confirmation'
3077
            );
3078
        }
3079
    }
3080
3081
    /**
3082
     * @param int $eventId
3083
     *
3084
     * @return array
3085
     */
3086
    public function getAllRepeatEvents($eventId)
3087
    {
3088
        $events = [];
3089
        $eventId = (int) $eventId;
3090
3091
        switch ($this->type) {
3092
            case 'personal':
3093
                break;
3094
            case 'course':
3095
                if (!empty($this->course['real_id'])) {
3096
                    $sql = "SELECT * FROM ".$this->tbl_course_agenda."
3097
                            WHERE
3098
                                c_id = ".$this->course['real_id']." AND
3099
                                parent_event_id = ".$eventId;
3100
                    $result = Database::query($sql);
3101
                    if (Database::num_rows($result)) {
3102
                        while ($row = Database::fetch_array($result, 'ASSOC')) {
3103
                            $events[] = $row;
3104
                        }
3105
                    }
3106
                }
3107
                break;
3108
        }
3109
3110
        return $events;
3111
    }
3112
3113
    /**
3114
     * @param int $eventId
3115
     * @param int $courseId
3116
     *
3117
     * @return bool
3118
     */
3119
    public function hasChildren($eventId, $courseId)
3120
    {
3121
        $eventId = (int) $eventId;
3122
        $courseId = (int) $courseId;
3123
3124
        $sql = "SELECT count(DISTINCT(id)) as count
3125
                FROM ".$this->tbl_course_agenda."
3126
                WHERE
3127
                    c_id = $courseId AND
3128
                    parent_event_id = $eventId";
3129
        $result = Database::query($sql);
3130
        if (Database::num_rows($result)) {
3131
            $row = Database::fetch_array($result, 'ASSOC');
3132
3133
            return $row['count'] > 0;
3134
        }
3135
3136
        return false;
3137
    }
3138
3139
    /**
3140
     * @param int    $filter
3141
     * @param string $view
3142
     *
3143
     * @return string
3144
     */
3145
    public function displayActions($view, $filter = 0)
3146
    {
3147
        $groupInfo = GroupManager::get_group_properties(api_get_group_id());
3148
        $groupIid = isset($groupInfo['iid']) ? $groupInfo['iid'] : 0;
3149
3150
        $codePath = api_get_path(WEB_CODE_PATH);
3151
3152
        $currentUserId = api_get_user_id();
3153
        $cidReq = api_get_cidreq();
3154
3155
        $actionsLeft = '';
3156
        $actionsLeft .= Display::url(
3157
            Display::return_icon('calendar.png', get_lang('Calendar'), [], ICON_SIZE_MEDIUM),
3158
            $codePath."calendar/agenda_js.php?type={$this->type}&$cidReq"
3159
        );
3160
        $actionsLeft .= Display::url(
3161
            Display::return_icon('week.png', get_lang('AgendaList'), [], ICON_SIZE_MEDIUM),
3162
            $codePath."calendar/agenda_list.php?type={$this->type}&$cidReq"
3163
        );
3164
3165
        $form = '';
3166
        if (api_is_allowed_to_edit(false, true) ||
3167
            ('personal' === $this->type && !api_is_anonymous() && 'true' === api_get_setting('allow_personal_agenda')) ||
3168
            (
3169
                '1' === api_get_course_setting('allow_user_edit_agenda') && !api_is_anonymous() &&
3170
                api_is_allowed_to_session_edit(false, true))
3171
            || (
3172
                GroupManager::user_has_access($currentUserId, $groupIid, GroupManager::GROUP_TOOL_CALENDAR)
3173
                && GroupManager::is_tutor_of_group($currentUserId, $groupInfo)
3174
            )
3175
        ) {
3176
            $actionsLeft .= Display::url(
3177
                Display::return_icon('new_event.png', get_lang('AgendaAdd'), [], ICON_SIZE_MEDIUM),
3178
                $codePath."calendar/agenda.php?action=add&type={$this->type}&$cidReq"
3179
            );
3180
3181
            $actionsLeft .= Display::url(
3182
                Display::return_icon('import_calendar.png', get_lang('ICalFileImport'), [], ICON_SIZE_MEDIUM),
3183
                $codePath."calendar/agenda.php?action=importical&type={$this->type}&$cidReq"
3184
            );
3185
3186
            if ($this->type === 'course') {
3187
                if (!isset($_GET['action'])) {
3188
                    $form = new FormValidator(
3189
                        'form-search',
3190
                        'post',
3191
                        '',
3192
                        '',
3193
                        [],
3194
                        FormValidator::LAYOUT_INLINE
3195
                    );
3196
                    $attributes = [
3197
                        'multiple' => false,
3198
                        'id' => 'select_form_id_search',
3199
                    ];
3200
                    $selectedValues = $this->parseAgendaFilter($filter);
3201
                    $this->showToForm($form, $selectedValues, $attributes);
3202
                    $form = $form->returnForm();
3203
                }
3204
            }
3205
        }
3206
3207
        if ($this->type === 'personal' && !api_is_anonymous()) {
3208
            $actionsLeft .= Display::url(
3209
                Display::return_icon('1day.png', get_lang('SessionsPlanCalendar'), [], ICON_SIZE_MEDIUM),
3210
                $codePath.'calendar/planification.php'
3211
            );
3212
3213
            if (api_is_student_boss() || api_is_platform_admin()) {
3214
                $actionsLeft .= Display::url(
3215
                    Display::return_icon('calendar-user.png', get_lang('MyStudentsSchedule'), [], ICON_SIZE_MEDIUM),
3216
                    $codePath.'mySpace/calendar_plan.php'
3217
                );
3218
            }
3219
        }
3220
3221
        if (api_is_platform_admin() ||
3222
            api_is_teacher() ||
3223
            api_is_student_boss() ||
3224
            api_is_drh() ||
3225
            api_is_session_admin() ||
3226
            api_is_coach()
3227
        ) {
3228
            if ($this->type == 'personal') {
3229
                $form = null;
3230
                if (!isset($_GET['action'])) {
3231
                    $form = new FormValidator(
3232
                        'form-search',
3233
                        'get',
3234
                        api_get_self().'?type=personal&',
3235
                        '',
3236
                        [],
3237
                        FormValidator::LAYOUT_INLINE
3238
                    );
3239
3240
                    $sessions = [];
3241
3242
                    if (api_is_drh()) {
3243
                        $sessionList = SessionManager::get_sessions_followed_by_drh($currentUserId);
3244
                        if (!empty($sessionList)) {
3245
                            foreach ($sessionList as $sessionItem) {
3246
                                $sessions[$sessionItem['id']] = strip_tags($sessionItem['name']);
3247
                            }
3248
                        }
3249
                    } else {
3250
                        $sessions = SessionManager::get_sessions_by_user($currentUserId);
3251
                        $sessions = array_column($sessions, 'session_name', 'session_id');
3252
                    }
3253
3254
                    $form->addHidden('type', 'personal');
3255
                    $sessions = ['0' => get_lang('SelectAnOption')] + $sessions;
3256
3257
                    $form->addSelect(
3258
                        'session_id',
3259
                        get_lang('Session'),
3260
                        $sessions,
3261
                        ['id' => 'session_id', 'onchange' => 'submit();']
3262
                    );
3263
3264
                    $form->addButtonReset(get_lang('Reset'));
3265
                    $form = $form->returnForm();
3266
                }
3267
            }
3268
        }
3269
3270
        $actionsRight = '';
3271
        if ($view == 'calendar') {
3272
            $actionsRight .= $form;
3273
        }
3274
3275
        $toolbar = Display::toolbarAction(
3276
            'toolbar-agenda',
3277
            [$actionsLeft, $actionsRight]
3278
        );
3279
3280
        return $toolbar;
3281
    }
3282
3283
    /**
3284
     * @return FormValidator
3285
     */
3286
    public function getImportCalendarForm()
3287
    {
3288
        $form = new FormValidator(
3289
            'frm_import_ical',
3290
            'post',
3291
            api_get_self().'?action=importical&type='.$this->type,
3292
            ['enctype' => 'multipart/form-data']
3293
        );
3294
        $form->addHeader(get_lang('ICalFileImport'));
3295
        $form->addElement('file', 'ical_import', get_lang('ICalFileImport'));
3296
        $form->addRule(
3297
            'ical_import',
3298
            get_lang('ThisFieldIsRequired'),
3299
            'required'
3300
        );
3301
        $form->addButtonImport(get_lang('Import'), 'ical_submit');
3302
3303
        return $form;
3304
    }
3305
3306
    /**
3307
     * @param array $courseInfo
3308
     * @param $file
3309
     *
3310
     * @return false|string
3311
     */
3312
    public function importEventFile($courseInfo, $file)
3313
    {
3314
        $charset = api_get_system_encoding();
3315
        $filepath = api_get_path(SYS_ARCHIVE_PATH).$file['name'];
3316
        $messages = [];
3317
3318
        if (!@move_uploaded_file($file['tmp_name'], $filepath)) {
3319
            error_log(
3320
                'Problem moving uploaded file: '.$file['error'].' in '.__FILE__.' line '.__LINE__
3321
            );
3322
3323
            return false;
3324
        }
3325
3326
        $data = file_get_contents($filepath);
3327
3328
        $trans = [
3329
            'DAILY' => 'daily',
3330
            'WEEKLY' => 'weekly',
3331
            'MONTHLY' => 'monthlyByDate',
3332
            'YEARLY' => 'yearly',
3333
        ];
3334
        $sentTo = ['everyone' => true];
3335
        $calendar = Sabre\VObject\Reader::read($data);
3336
        $currentTimeZone = api_get_timezone();
3337
        if (!empty($calendar->VEVENT)) {
3338
            /** @var Sabre\VObject\Component\VEvent $event */
3339
            foreach ($calendar->VEVENT as $event) {
3340
                $tempDate = $event->DTSTART->getValue();
3341
                if ('Z' == substr($tempDate, -1) && 'UTC' != date('e', strtotime($tempDate))) {
3342
                    $event->DTSTART->setValue(gmdate('Ymd\THis\Z', strtotime($tempDate)));
3343
                }
3344
                $tempDate = $event->DTEND->getValue();
3345
                if ('Z' == substr($tempDate, -1) && 'UTC' != date('e', strtotime($tempDate))) {
3346
                    $event->DTEND->setValue(gmdate('Ymd\THis\Z', strtotime($tempDate)));
3347
                }
3348
                $start = $event->DTSTART->getDateTime();
3349
                $end = $event->DTEND->getDateTime();
3350
                //Sabre\VObject\DateTimeParser::parseDateTime(string $dt, \Sabre\VObject\DateTimeZone $tz)
3351
3352
                $startDateTime = api_get_local_time(
3353
                    $start->format('Y-m-d H:i:s'),
3354
                    $currentTimeZone,
3355
                    $start->format('e')
3356
                );
3357
                $endDateTime = api_get_local_time(
3358
                    $end->format('Y-m-d H:i'),
3359
                    $currentTimeZone,
3360
                    $end->format('e')
3361
                );
3362
                $title = api_convert_encoding(
3363
                    (string) $event->summary,
3364
                    $charset,
3365
                    'UTF-8'
3366
                );
3367
                $description = api_convert_encoding(
3368
                    (string) $event->description,
3369
                    $charset,
3370
                    'UTF-8'
3371
                );
3372
3373
                $id = $this->addEvent(
3374
                    $startDateTime,
3375
                    $endDateTime,
3376
                    'false',
3377
                    $title,
3378
                    $description,
3379
                    $sentTo
3380
                );
3381
3382
                $messages[] = " $title - ".$startDateTime." - ".$endDateTime;
3383
3384
                //$attendee = (string)$event->attendee;
3385
                /** @var Sabre\VObject\Property\ICalendar\Recur $repeat */
3386
                $repeat = $event->RRULE;
3387
                if ($id && !empty($repeat)) {
3388
                    $repeat = $repeat->getParts();
3389
                    $freq = $trans[$repeat['FREQ']];
3390
3391
                    if (isset($repeat['UNTIL']) && !empty($repeat['UNTIL'])) {
3392
                        // Check if datetime or just date (strlen == 8)
3393
                        if (strlen($repeat['UNTIL']) == 8) {
3394
                            // Fix the datetime format to avoid exception in the next step
3395
                            $repeat['UNTIL'] .= 'T000000';
3396
                        }
3397
                        $until = Sabre\VObject\DateTimeParser::parseDateTime(
3398
                            $repeat['UNTIL'],
3399
                            new DateTimeZone($currentTimeZone)
3400
                        );
3401
                        $until = $until->format('Y-m-d H:i:s');
3402
                        $this->addRepeatedItem(
3403
                            $id,
3404
                            $freq,
3405
                            $until,
3406
                            $sentTo
3407
                        );
3408
                    }
3409
3410
                    if (!empty($repeat['COUNT'])) {
3411
                        /*$count = $repeat['COUNT'];
3412
                        $interval = $repeat['INTERVAL'];
3413
                        $endDate = null;
3414
                        switch($freq) {
3415
                            case 'daily':
3416
                                $start = api_strtotime($startDateTime);
3417
                                $date = new DateTime($startDateTime);
3418
                                $days = $count * $interval;
3419
                                var_dump($days);
3420
                                $date->add(new DateInterval("P".$days."D"));
3421
                                $endDate = $date->format('Y-m-d H:i');
3422
                                //$endDate = $count *
3423
                                for ($i = 0; $i < $count; $i++) {
3424
                                    $days = 86400 * 7
3425
                                }
3426
                            }
3427
                        }*/
3428
                        //$res = agenda_add_repeat_item($courseInfo, $id, $freq, $count, $attendee);
3429
                        /*$this->addRepeatedItem(
3430
                            $id,
3431
                            $freq,
3432
                            $endDate,
3433
                            $sentTo
3434
                        );*/
3435
                    }
3436
                }
3437
            }
3438
        }
3439
3440
        if (!empty($messages)) {
3441
            $messages = implode('<br /> ', $messages);
3442
        } else {
3443
            $messages = get_lang('NoAgendaItems');
3444
        }
3445
3446
        return $messages;
3447
    }
3448
3449
    /**
3450
     * Parse filter turns USER:12 to ['users' => [12])] or G:1 ['groups' => [1]].
3451
     *
3452
     * @param int $filter
3453
     *
3454
     * @return array
3455
     */
3456
    public function parseAgendaFilter($filter)
3457
    {
3458
        $everyone = false;
3459
        $groupId = null;
3460
        $userId = null;
3461
3462
        if ($filter == 'everyone') {
3463
            $everyone = true;
3464
        } else {
3465
            if (substr($filter, 0, 1) == 'G') {
3466
                $groupId = str_replace('GROUP:', '', $filter);
3467
            } else {
3468
                $userId = str_replace('USER:', '', $filter);
3469
            }
3470
        }
3471
        if (empty($userId) && empty($groupId)) {
3472
            $everyone = true;
3473
        }
3474
3475
        return [
3476
            'everyone' => $everyone,
3477
            'users' => [$userId],
3478
            'groups' => [$groupId],
3479
        ];
3480
    }
3481
3482
    /**
3483
     *    This function retrieves all the agenda items of all the courses the user is subscribed to.
3484
     */
3485
    public static function get_myagendaitems(
3486
        $user_id,
3487
        $courses_dbs,
3488
        $month,
3489
        $year
3490
    ) {
3491
        $user_id = intval($user_id);
3492
3493
        $items = [];
3494
        $my_list = [];
3495
3496
        // get agenda-items for every course
3497
        foreach ($courses_dbs as $key => $array_course_info) {
3498
            //databases of the courses
3499
            $TABLEAGENDA = Database::get_course_table(TABLE_AGENDA);
3500
            $TABLE_ITEMPROPERTY = Database::get_course_table(
3501
                TABLE_ITEM_PROPERTY
3502
            );
3503
3504
            $group_memberships = GroupManager::get_group_ids(
3505
                $array_course_info['real_id'],
3506
                $user_id
3507
            );
3508
            $course_user_status = CourseManager::getUserInCourseStatus(
3509
                $user_id,
3510
                $array_course_info['real_id']
3511
            );
3512
            // if the user is administrator of that course we show all the agenda items
3513
            if ($course_user_status == '1') {
3514
                //echo "course admin";
3515
                $sqlquery = "SELECT DISTINCT agenda.*, ip.visibility, ip.to_group_id, ip.insert_user_id, ip.ref
3516
							FROM ".$TABLEAGENDA." agenda,
3517
								 ".$TABLE_ITEMPROPERTY." ip
3518
							WHERE agenda.id = ip.ref
3519
							AND MONTH(agenda.start_date)='".$month."'
3520
							AND YEAR(agenda.start_date)='".$year."'
3521
							AND ip.tool='".TOOL_CALENDAR_EVENT."'
3522
							AND ip.visibility='1'
3523
							GROUP BY agenda.id
3524
							ORDER BY start_date ";
3525
            } else {
3526
                // if the user is not an administrator of that course
3527
                if (is_array($group_memberships) && count(
3528
                        $group_memberships
3529
                    ) > 0
3530
                ) {
3531
                    $sqlquery = "SELECT	agenda.*, ip.visibility, ip.to_group_id, ip.insert_user_id, ip.ref
3532
								FROM ".$TABLEAGENDA." agenda,
3533
									".$TABLE_ITEMPROPERTY." ip
3534
								WHERE agenda.id = ip.ref
3535
								AND MONTH(agenda.start_date)='".$month."'
3536
								AND YEAR(agenda.start_date)='".$year."'
3537
								AND ip.tool='".TOOL_CALENDAR_EVENT."'
3538
								AND	( ip.to_user_id='".$user_id."' OR (ip.to_group_id IS NULL OR ip.to_group_id IN (0, ".implode(
3539
                            ", ",
3540
                            $group_memberships
3541
                        ).")) )
3542
								AND ip.visibility='1'
3543
								ORDER BY start_date ";
3544
                } else {
3545
                    $sqlquery = "SELECT agenda.*, ip.visibility, ip.to_group_id, ip.insert_user_id, ip.ref
3546
								FROM ".$TABLEAGENDA." agenda,
3547
									".$TABLE_ITEMPROPERTY." ip
3548
								WHERE agenda.id = ip.ref
3549
								AND MONTH(agenda.start_date)='".$month."'
3550
								AND YEAR(agenda.start_date)='".$year."'
3551
								AND ip.tool='".TOOL_CALENDAR_EVENT."'
3552
								AND ( ip.to_user_id='".$user_id."' OR ip.to_group_id='0' OR ip.to_group_id IS NULL)
3553
								AND ip.visibility='1'
3554
								ORDER BY start_date ";
3555
                }
3556
            }
3557
            $result = Database::query($sqlquery);
3558
3559
            while ($item = Database::fetch_array($result, 'ASSOC')) {
3560
                $agendaday = -1;
3561
                if (!empty($item['start_date'])) {
3562
                    $item['start_date'] = api_get_local_time(
3563
                        $item['start_date']
3564
                    );
3565
                    $item['start_date_tms'] = api_strtotime(
3566
                        $item['start_date']
3567
                    );
3568
                    $agendaday = date("j", $item['start_date_tms']);
3569
                }
3570
                if (!empty($item['end_date'])) {
3571
                    $item['end_date'] = api_get_local_time($item['end_date']);
3572
                }
3573
3574
                $url = api_get_path(
3575
                        WEB_CODE_PATH
3576
                    )."calendar/agenda.php?cidReq=".urlencode(
3577
                        $array_course_info["code"]
3578
                    )."&day=$agendaday&month=$month&year=$year#$agendaday";
3579
3580
                $item['url'] = $url;
3581
                $item['course_name'] = $array_course_info['title'];
3582
                $item['calendar_type'] = 'course';
3583
                $item['course_id'] = $array_course_info['course_id'];
3584
3585
                $my_list[$agendaday][] = $item;
3586
            }
3587
        }
3588
3589
        // sorting by hour for every day
3590
        $agendaitems = [];
3591
        foreach ($items as $agendaday => $tmpitems) {
3592
            if (!isset($agendaitems[$agendaday])) {
3593
                $agendaitems[$agendaday] = '';
3594
            }
3595
            sort($tmpitems);
3596
            foreach ($tmpitems as $val) {
3597
                $agendaitems[$agendaday] .= $val;
3598
            }
3599
        }
3600
3601
        return $my_list;
3602
    }
3603
3604
    /**
3605
     * This function retrieves one personal agenda item returns it.
3606
     *
3607
     * @param    array    The array containing existing events. We add to this array.
3608
     * @param    int        Day
3609
     * @param    int        Month
3610
     * @param    int        Year (4 digits)
3611
     * @param    int        Week number
3612
     * @param    string    Type of view (month_view, week_view, day_view)
3613
     *
3614
     * @return array The results of the database query, or null if not found
3615
     */
3616
    public static function get_global_agenda_items(
3617
        $agendaitems,
3618
        $day,
3619
        $month,
3620
        $year,
3621
        $week,
3622
        $type
3623
    ) {
3624
        $tbl_global_agenda = Database::get_main_table(
3625
            TABLE_MAIN_SYSTEM_CALENDAR
3626
        );
3627
        $month = intval($month);
3628
        $year = intval($year);
3629
        $week = intval($week);
3630
        $day = intval($day);
3631
        // 1. creating the SQL statement for getting the personal agenda items in MONTH view
3632
3633
        $current_access_url_id = api_get_current_access_url_id();
3634
3635
        if ($type == "month_view" || $type == "") {
3636
            // We are in month view
3637
            $sql = "SELECT * FROM ".$tbl_global_agenda."
3638
                    WHERE
3639
                        MONTH(start_date) = ".$month." AND
3640
                        YEAR(start_date) = ".$year."  AND
3641
                        access_url_id = $current_access_url_id
3642
                    ORDER BY start_date ASC";
3643
        }
3644
        // 2. creating the SQL statement for getting the personal agenda items in WEEK view
3645
        if ($type == "week_view") { // we are in week view
3646
            $start_end_day_of_week = self::calculate_start_end_of_week(
3647
                $week,
3648
                $year
3649
            );
3650
            $start_day = $start_end_day_of_week['start']['day'];
3651
            $start_month = $start_end_day_of_week['start']['month'];
3652
            $start_year = $start_end_day_of_week['start']['year'];
3653
            $end_day = $start_end_day_of_week['end']['day'];
3654
            $end_month = $start_end_day_of_week['end']['month'];
3655
            $end_year = $start_end_day_of_week['end']['year'];
3656
            // in sql statements you have to use year-month-day for date calculations
3657
            $start_filter = $start_year."-".$start_month."-".$start_day." 00:00:00";
3658
            $start_filter = api_get_utc_datetime($start_filter);
3659
3660
            $end_filter = $end_year."-".$end_month."-".$end_day." 23:59:59";
3661
            $end_filter = api_get_utc_datetime($end_filter);
3662
            $sql = " SELECT * FROM ".$tbl_global_agenda." WHERE start_date>='".$start_filter."' AND start_date<='".$end_filter."' AND  access_url_id = $current_access_url_id ";
3663
        }
3664
        // 3. creating the SQL statement for getting the personal agenda items in DAY view
3665
        if ($type == "day_view") { // we are in day view
3666
            // we could use mysql date() function but this is only available from 4.1 and higher
3667
            $start_filter = $year."-".$month."-".$day." 00:00:00";
3668
            $start_filter = api_get_utc_datetime($start_filter);
3669
3670
            $end_filter = $year."-".$month."-".$day." 23:59:59";
3671
            $end_filter = api_get_utc_datetime($end_filter);
3672
            $sql = " SELECT * FROM ".$tbl_global_agenda." WHERE start_date>='".$start_filter."' AND start_date<='".$end_filter."'  AND  access_url_id = $current_access_url_id";
3673
        }
3674
3675
        $result = Database::query($sql);
3676
3677
        while ($item = Database::fetch_array($result)) {
3678
            if (!empty($item['start_date'])) {
3679
                $item['start_date'] = api_get_local_time($item['start_date']);
3680
                $item['start_date_tms'] = api_strtotime($item['start_date']);
3681
            }
3682
            if (!empty($item['end_date'])) {
3683
                $item['end_date'] = api_get_local_time($item['end_date']);
3684
            }
3685
3686
            // we break the date field in the database into a date and a time part
3687
            $agenda_db_date = explode(" ", $item['start_date']);
3688
            $date = $agenda_db_date[0];
3689
            $time = $agenda_db_date[1];
3690
            // we divide the date part into a day, a month and a year
3691
            $agendadate = explode("-", $date);
3692
            $year = intval($agendadate[0]);
3693
            $month = intval($agendadate[1]);
3694
            $day = intval($agendadate[2]);
3695
            // we divide the time part into hour, minutes, seconds
3696
            $agendatime = explode(":", $time);
3697
            $hour = $agendatime[0];
3698
            $minute = $agendatime[1];
3699
            $second = $agendatime[2];
3700
3701
            if ($type == 'month_view') {
3702
                $item['calendar_type'] = 'global';
3703
                $agendaitems[$day][] = $item;
3704
                continue;
3705
            }
3706
3707
            $start_time = api_format_date(
3708
                $item['start_date'],
3709
                TIME_NO_SEC_FORMAT
3710
            );
3711
            $end_time = '';
3712
            if (!empty($item['end_date'])) {
3713
                $end_time = ' - '.api_format_date(
3714
                        $item['end_date'],
3715
                        DATE_TIME_FORMAT_LONG
3716
                    );
3717
            }
3718
3719
            // if the student has specified a course we a add a link to that course
3720
            if ($item['course'] != "") {
3721
                $url = api_get_path(
3722
                        WEB_CODE_PATH
3723
                    )."admin/agenda.php?cidReq=".urlencode(
3724
                        $item['course']
3725
                    )."&day=$day&month=$month&year=$year#$day"; // RH  //Patrick Cool: to highlight the relevant agenda item
3726
                $course_link = "<a href=\"$url\" title=\"".$item['course']."\">".$item['course']."</a>";
3727
            } else {
3728
                $course_link = "";
3729
            }
3730
            // Creating the array that will be returned. If we have week or month view we have an array with the date as the key
3731
            // if we have a day_view we use a half hour as index => key 33 = 16h30
3732
            if ($type !== "day_view") {
3733
                // This is the array construction for the WEEK or MONTH view
3734
                //Display the Agenda global in the tab agenda (administrator)
3735
                $agendaitems[$day] .= "<i>$start_time $end_time</i>&nbsp;-&nbsp;";
3736
                $agendaitems[$day] .= "<b>".get_lang('GlobalEvent')."</b>";
3737
                $agendaitems[$day] .= "<div>".$item['title']."</div><br>";
3738
            } else {
3739
                // this is the array construction for the DAY view
3740
                $halfhour = 2 * $agendatime['0'];
3741
                if ($agendatime['1'] >= '30') {
3742
                    $halfhour = $halfhour + 1;
3743
                }
3744
                if (!is_array($agendaitems[$halfhour])) {
3745
                    $content = $agendaitems[$halfhour];
3746
                }
3747
                $agendaitems[$halfhour] = $content."<div><i>$hour:$minute</i> <b>".get_lang(
3748
                        'GlobalEvent'
3749
                    ).":  </b>".$item['title']."</div>";
3750
            }
3751
        }
3752
3753
        return $agendaitems;
3754
    }
3755
3756
    /**
3757
     * This function retrieves all the personal agenda items and add them to the agenda items found by the other
3758
     * functions.
3759
     */
3760
    public static function get_personal_agenda_items(
3761
        $user_id,
3762
        $agendaitems,
3763
        $day,
3764
        $month,
3765
        $year,
3766
        $week,
3767
        $type
3768
    ) {
3769
        $tbl_personal_agenda = Database::get_main_table(TABLE_PERSONAL_AGENDA);
3770
        $user_id = intval($user_id);
3771
3772
        // 1. creating the SQL statement for getting the personal agenda items in MONTH view
3773
        if ($type === "month_view" || $type === "") {
3774
            // we are in month view
3775
            $sql = "SELECT * FROM $tbl_personal_agenda
3776
                    WHERE
3777
                        user='".$user_id."' AND
3778
                        MONTH(date)='".$month."' AND
3779
                        YEAR(date) = '".$year."'
3780
                     ORDER BY date ASC";
3781
        }
3782
3783
        // 2. creating the SQL statement for getting the personal agenda items in WEEK view
3784
        // we are in week view
3785
        if ($type == "week_view") {
3786
            $start_end_day_of_week = self::calculate_start_end_of_week(
3787
                $week,
3788
                $year
3789
            );
3790
            $start_day = $start_end_day_of_week['start']['day'];
3791
            $start_month = $start_end_day_of_week['start']['month'];
3792
            $start_year = $start_end_day_of_week['start']['year'];
3793
            $end_day = $start_end_day_of_week['end']['day'];
3794
            $end_month = $start_end_day_of_week['end']['month'];
3795
            $end_year = $start_end_day_of_week['end']['year'];
3796
            // in sql statements you have to use year-month-day for date calculations
3797
            $start_filter = $start_year."-".$start_month."-".$start_day." 00:00:00";
3798
            $start_filter = api_get_utc_datetime($start_filter);
3799
            $end_filter = $end_year."-".$end_month."-".$end_day." 23:59:59";
3800
            $end_filter = api_get_utc_datetime($end_filter);
3801
            $sql = " SELECT * FROM ".$tbl_personal_agenda." WHERE user='".$user_id."' AND date>='".$start_filter."' AND date<='".$end_filter."'";
3802
        }
3803
        // 3. creating the SQL statement for getting the personal agenda items in DAY view
3804
        if ($type == "day_view") {
3805
            // we are in day view
3806
            // we could use mysql date() function but this is only available from 4.1 and higher
3807
            $start_filter = $year."-".$month."-".$day." 00:00:00";
3808
            $start_filter = api_get_utc_datetime($start_filter);
3809
            $end_filter = $year."-".$month."-".$day." 23:59:59";
3810
            $end_filter = api_get_utc_datetime($end_filter);
3811
            $sql = " SELECT * FROM ".$tbl_personal_agenda." WHERE user='".$user_id."' AND date>='".$start_filter."' AND date<='".$end_filter."'";
3812
        }
3813
3814
        $result = Database::query($sql);
3815
        while ($item = Database::fetch_array($result, 'ASSOC')) {
3816
            $time_minute = api_convert_and_format_date(
3817
                $item['date'],
3818
                TIME_NO_SEC_FORMAT
3819
            );
3820
            $item['date'] = api_get_local_time($item['date']);
3821
            $item['start_date_tms'] = api_strtotime($item['date']);
3822
            $item['content'] = $item['text'];
3823
3824
            // we break the date field in the database into a date and a time part
3825
            $agenda_db_date = explode(" ", $item['date']);
3826
            $date = $agenda_db_date[0];
3827
            $time = $agenda_db_date[1];
3828
            // we divide the date part into a day, a month and a year
3829
            $agendadate = explode("-", $item['date']);
3830
            $year = intval($agendadate[0]);
3831
            $month = intval($agendadate[1]);
3832
            $day = intval($agendadate[2]);
3833
            // we divide the time part into hour, minutes, seconds
3834
            $agendatime = explode(":", $time);
3835
3836
            $hour = $agendatime[0];
3837
            $minute = $agendatime[1];
3838
            $second = $agendatime[2];
3839
3840
            if ($type == 'month_view') {
3841
                $item['calendar_type'] = 'personal';
3842
                $item['start_date'] = $item['date'];
3843
                $agendaitems[$day][] = $item;
3844
                continue;
3845
            }
3846
3847
            // if the student has specified a course we a add a link to that course
3848
            if ($item['course'] != "") {
3849
                $url = api_get_path(
3850
                        WEB_CODE_PATH
3851
                    )."calendar/agenda.php?cidReq=".urlencode(
3852
                        $item['course']
3853
                    )."&day=$day&month=$month&year=$year#$day"; // RH  //Patrick Cool: to highlight the relevant agenda item
3854
                $course_link = "<a href=\"$url\" title=\"".$item['course']."\">".$item['course']."</a>";
3855
            } else {
3856
                $course_link = "";
3857
            }
3858
            // Creating the array that will be returned. If we have week or month view we have an array with the date as the key
3859
            // if we have a day_view we use a half hour as index => key 33 = 16h30
3860
            if ($type !== "day_view") {
3861
                // This is the array construction for the WEEK or MONTH view
3862
3863
                //Display events in agenda
3864
                $agendaitems[$day] .= "<div><i>$time_minute</i> $course_link <a href=\"myagenda.php?action=view&view=personal&day=$day&month=$month&year=$year&id=".$item['id']."#".$item['id']."\" class=\"personal_agenda\">".$item['title']."</a></div><br />";
3865
            } else {
3866
                // this is the array construction for the DAY view
3867
                $halfhour = 2 * $agendatime['0'];
3868
                if ($agendatime['1'] >= '30') {
3869
                    $halfhour = $halfhour + 1;
3870
                }
3871
3872
                //Display events by list
3873
                $agendaitems[$halfhour] .= "<div><i>$time_minute</i> $course_link <a href=\"myagenda.php?action=view&view=personal&day=$day&month=$month&year=$year&id=".$item['id']."#".$item['id']."\" class=\"personal_agenda\">".$item['title']."</a></div>";
3874
            }
3875
        }
3876
3877
        return $agendaitems;
3878
    }
3879
3880
    /**
3881
     * Show the monthcalender of the given month.
3882
     *
3883
     * @param    array    Agendaitems
3884
     * @param    int    Month number
3885
     * @param    int    Year number
3886
     * @param    array    Array of strings containing long week day names (deprecated, you can send an empty array
3887
     *                          instead)
3888
     * @param    string    The month name
3889
     */
3890
    public static function display_mymonthcalendar(
3891
        $user_id,
3892
        $agendaitems,
3893
        $month,
3894
        $year,
3895
        $weekdaynames,
3896
        $monthName,
3897
        $show_content = true
3898
    ) {
3899
        global $DaysShort, $course_path;
3900
        //Handle leap year
3901
        $numberofdays = [
3902
            0,
3903
            31,
3904
            28,
3905
            31,
3906
            30,
3907
            31,
3908
            30,
3909
            31,
3910
            31,
3911
            30,
3912
            31,
3913
            30,
3914
            31,
3915
        ];
3916
        if (($year % 400 == 0) or ($year % 4 == 0 and $year % 100 != 0)) {
3917
            $numberofdays[2] = 29;
3918
        }
3919
        //Get the first day of the month
3920
        $dayone = getdate(mktime(0, 0, 0, $month, 1, $year));
3921
        //Start the week on monday
3922
        $startdayofweek = $dayone['wday'] != 0 ? ($dayone['wday'] - 1) : 6;
3923
        $g_cc = (isset($_GET['courseCode']) ? $_GET['courseCode'] : '');
3924
3925
        $next_month = ($month == 1 ? 12 : $month - 1);
3926
        $prev_month = ($month == 12 ? 1 : $month + 1);
3927
3928
        $next_year = ($month == 1 ? $year - 1 : $year);
3929
        $prev_year = ($month == 12 ? $year + 1 : $year);
3930
3931
        if ($show_content) {
3932
            $back_url = Display::url(
3933
                get_lang('Previous'),
3934
                api_get_self()."?coursePath=".urlencode(
3935
                    $course_path
3936
                )."&courseCode=".Security::remove_XSS(
3937
                    $g_cc
3938
                )."&action=view&view=month&month=".$next_month."&year=".$next_year
3939
            );
3940
            $next_url = Display::url(
3941
                get_lang('Next'),
3942
                api_get_self()."?coursePath=".urlencode(
3943
                    $course_path
3944
                )."&courseCode=".Security::remove_XSS(
3945
                    $g_cc
3946
                )."&action=view&view=month&month=".$prev_month."&year=".$prev_year
3947
            );
3948
        } else {
3949
            $back_url = Display::url(
3950
                get_lang('Previous'),
3951
                '',
3952
                [
3953
                    'onclick' => "load_calendar('".$user_id."','".$next_month."', '".$next_year."'); ",
3954
                    'class' => 'btn ui-button ui-widget ui-state-default',
3955
                ]
3956
            );
3957
            $next_url = Display::url(
3958
                get_lang('Next'),
3959
                '',
3960
                [
3961
                    'onclick' => "load_calendar('".$user_id."','".$prev_month."', '".$prev_year."'); ",
3962
                    'class' => 'pull-right btn ui-button ui-widget ui-state-default',
3963
                ]
3964
            );
3965
        }
3966
        $html = '';
3967
        $html .= '<div class="actions">';
3968
        $html .= '<div class="row">';
3969
        $html .= '<div class="col-md-4">'.$back_url.'</div>';
3970
        $html .= '<div class="col-md-4"><p class="agenda-title text-center">'.$monthName." ".$year.'</p></div>';
3971
        $html .= '<div class="col-md-4">'.$next_url.'</div>';
3972
        $html .= '</div>';
3973
        $html .= '</div>';
3974
        $html .= '<table id="agenda_list2" class="table table-bordered">';
3975
        $html .= '<tr>';
3976
        for ($ii = 1; $ii < 8; $ii++) {
3977
            $html .= '<td class="weekdays">'.$DaysShort[$ii % 7].'</td>';
3978
        }
3979
        $html .= '</tr>';
3980
3981
        $curday = -1;
3982
        $today = getdate();
3983
        while ($curday <= $numberofdays[$month]) {
3984
            $html .= "<tr>";
3985
            for ($ii = 0; $ii < 7; $ii++) {
3986
                if (($curday == -1) && ($ii == $startdayofweek)) {
3987
                    $curday = 1;
3988
                }
3989
                if (($curday > 0) && ($curday <= $numberofdays[$month])) {
3990
                    $bgcolor = $class = 'class="days_week"';
3991
                    $dayheader = Display::div(
3992
                        $curday,
3993
                        ['class' => 'agenda_day']
3994
                    );
3995
                    if (($curday == $today['mday']) && ($year == $today['year']) && ($month == $today['mon'])) {
3996
                        $class = "class=\"days_today\" style=\"width:10%;\"";
3997
                    }
3998
3999
                    $html .= "<td ".$class.">".$dayheader;
4000
4001
                    if (!empty($agendaitems[$curday])) {
4002
                        $items = $agendaitems[$curday];
4003
                        $items = msort($items, 'start_date_tms');
4004
4005
                        foreach ($items as $value) {
4006
                            $value['title'] = Security::remove_XSS(
4007
                                $value['title']
4008
                            );
4009
                            $start_time = api_format_date(
4010
                                $value['start_date'],
4011
                                TIME_NO_SEC_FORMAT
4012
                            );
4013
                            $end_time = '';
4014
4015
                            if (!empty($value['end_date'])) {
4016
                                $end_time = '-&nbsp;<i>'.api_format_date(
4017
                                        $value['end_date'],
4018
                                        DATE_TIME_FORMAT_LONG
4019
                                    ).'</i>';
4020
                            }
4021
                            $complete_time = '<i>'.api_format_date(
4022
                                    $value['start_date'],
4023
                                    DATE_TIME_FORMAT_LONG
4024
                                ).'</i>&nbsp;'.$end_time;
4025
                            $time = '<i>'.$start_time.'</i>';
4026
4027
                            switch ($value['calendar_type']) {
4028
                                case 'personal':
4029
                                    $bg_color = '#D0E7F4';
4030
                                    $icon = Display::return_icon(
4031
                                        'user.png',
4032
                                        get_lang('MyAgenda'),
4033
                                        [],
4034
                                        ICON_SIZE_SMALL
4035
                                    );
4036
                                    break;
4037
                                case 'global':
4038
                                    $bg_color = '#FFBC89';
4039
                                    $icon = Display::return_icon(
4040
                                        'view_remove.png',
4041
                                        get_lang('GlobalEvent'),
4042
                                        [],
4043
                                        ICON_SIZE_SMALL
4044
                                    );
4045
                                    break;
4046
                                case 'course':
4047
                                    $bg_color = '#CAFFAA';
4048
                                    $icon_name = 'course.png';
4049
                                    if (!empty($value['session_id'])) {
4050
                                        $icon_name = 'session.png';
4051
                                    }
4052
                                    if ($show_content) {
4053
                                        $icon = Display::url(
4054
                                            Display::return_icon(
4055
                                                $icon_name,
4056
                                                $value['course_name'].' '.get_lang(
4057
                                                    'Course'
4058
                                                ),
4059
                                                [],
4060
                                                ICON_SIZE_SMALL
4061
                                            ),
4062
                                            $value['url']
4063
                                        );
4064
                                    } else {
4065
                                        $icon = Display::return_icon(
4066
                                            $icon_name,
4067
                                            $value['course_name'].' '.get_lang(
4068
                                                'Course'
4069
                                            ),
4070
                                            [],
4071
                                            ICON_SIZE_SMALL
4072
                                        );
4073
                                    }
4074
                                    break;
4075
                                default:
4076
                                    break;
4077
                            }
4078
4079
                            $result = '<div class="rounded_div_agenda" style="background-color:'.$bg_color.';">';
4080
4081
                            if ($show_content) {
4082
                                //Setting a personal event to green
4083
                                $icon = Display::div(
4084
                                    $icon,
4085
                                    ['style' => 'float:right']
4086
                                );
4087
4088
                                $link = $value['calendar_type'].'_'.$value['id'].'_'.$value['course_id'].'_'.$value['session_id'];
4089
4090
                                //Link to bubble
4091
                                $url = Display::url(
4092
                                    cut($value['title'], 40),
4093
                                    '#',
4094
                                    ['id' => $link, 'class' => 'opener']
4095
                                );
4096
                                $result .= $time.' '.$icon.' '.Display::div(
4097
                                        $url
4098
                                    );
4099
4100
                                //Hidden content
4101
                                $content = Display::div(
4102
                                    $icon.Display::tag(
4103
                                        'h2',
4104
                                        $value['course_name']
4105
                                    ).'<hr />'.Display::tag(
4106
                                        'h3',
4107
                                        $value['title']
4108
                                    ).$complete_time.'<hr />'.Security::remove_XSS(
4109
                                        $value['content']
4110
                                    )
4111
                                );
4112
4113
                                //Main div
4114
                                $result .= Display::div(
4115
                                    $content,
4116
                                    [
4117
                                        'id' => 'main_'.$link,
4118
                                        'class' => 'dialog',
4119
                                        'style' => 'display:none',
4120
                                    ]
4121
                                );
4122
                                $result .= '</div>';
4123
                                $html .= $result;
4124
                            } else {
4125
                                $html .= $result .= $icon.'</div>';
4126
                            }
4127
                        }
4128
                    }
4129
                    $html .= "</td>";
4130
                    $curday++;
4131
                } else {
4132
                    $html .= "<td></td>";
4133
                }
4134
            }
4135
            $html .= "</tr>";
4136
        }
4137
        $html .= "</table>";
4138
        echo $html;
4139
    }
4140
4141
    /**
4142
     * Get personal agenda items between two dates (=all events from all registered courses).
4143
     *
4144
     * @param int $user_id user ID of the user
4145
     * @param    string    Optional start date in datetime format (if no start date is given, uses today)
4146
     * @param    string    Optional end date in datetime format (if no date is given, uses one year from now)
4147
     *
4148
     * @return array array of events ordered by start date, in
4149
     *               [0]('datestart','dateend','title'),[1]('datestart','dateend','title','link','coursetitle') format,
4150
     *               where datestart and dateend are in yyyyMMddhhmmss format
4151
     *
4152
     * @deprecated use agenda events
4153
     */
4154
    public static function get_personal_agenda_items_between_dates(
4155
        $user_id,
4156
        $date_start = '',
4157
        $date_end = ''
4158
    ) {
4159
        $items = [];
4160
        if ($user_id != strval(intval($user_id))) {
4161
            return $items;
4162
        }
4163
        if (empty($date_start)) {
4164
            $date_start = date('Y-m-d H:i:s');
4165
        }
4166
        if (empty($date_end)) {
4167
            $date_end = date(
4168
                'Y-m-d H:i:s',
4169
                mktime(0, 0, 0, date("m"), date("d"), date("Y") + 1)
4170
            );
4171
        }
4172
        $expr = '/\d{4}-\d{2}-\d{2}\ \d{2}:\d{2}:\d{2}/';
4173
        if (!preg_match($expr, $date_start)) {
4174
            return $items;
4175
        }
4176
        if (!preg_match($expr, $date_end)) {
4177
            return $items;
4178
        }
4179
4180
        // get agenda-items for every course
4181
        $courses = api_get_user_courses($user_id, false);
4182
        foreach ($courses as $id => $course) {
4183
            $c = api_get_course_info_by_id($course['real_id']);
4184
            //databases of the courses
4185
            $t_a = Database::get_course_table(TABLE_AGENDA, $course['db']);
4186
            $t_ip = Database::get_course_table(
4187
                TABLE_ITEM_PROPERTY,
4188
                $course['db']
4189
            );
4190
            // get the groups to which the user belong
4191
            $group_memberships = GroupManager:: get_group_ids(
4192
                $course['db'],
4193
                $user_id
4194
            );
4195
            // if the user is administrator of that course we show all the agenda items
4196
            if ($course['status'] == '1') {
4197
                //echo "course admin";
4198
                $sqlquery = "SELECT ".
4199
                    " DISTINCT agenda.*, ip.visibility, ip.to_group_id, ip.insert_user_id, ip.ref ".
4200
                    " FROM ".$t_a." agenda, ".
4201
                    $t_ip." ip ".
4202
                    " WHERE agenda.id = ip.ref ".
4203
                    " AND agenda.start_date>='$date_start' ".
4204
                    " AND agenda.end_date<='$date_end' ".
4205
                    " AND ip.tool='".TOOL_CALENDAR_EVENT."' ".
4206
                    " AND ip.visibility='1' ".
4207
                    " GROUP BY agenda.id ".
4208
                    " ORDER BY start_date ";
4209
            } else {
4210
                // if the user is not an administrator of that course, then...
4211
                if (is_array($group_memberships) && count(
4212
                        $group_memberships
4213
                    ) > 0
4214
                ) {
4215
                    $sqlquery = "SELECT ".
4216
                        "DISTINCT agenda.*, ip.visibility, ip.to_group_id, ip.insert_user_id, ip.ref ".
4217
                        " FROM ".$t_a." agenda, ".
4218
                        $t_ip." ip ".
4219
                        " WHERE agenda.id = ip.ref ".
4220
                        " AND agenda.start_date>='$date_start' ".
4221
                        " AND agenda.end_date<='$date_end' ".
4222
                        " AND ip.tool='".TOOL_CALENDAR_EVENT."' ".
4223
                        " AND	( ip.to_user_id='".$user_id."' OR (ip.to_group_id IS NULL OR ip.to_group_id IN (0, ".implode(
4224
                            ", ",
4225
                            $group_memberships
4226
                        ).")) ) ".
4227
                        " AND ip.visibility='1' ".
4228
                        " ORDER BY start_date ";
4229
                } else {
4230
                    $sqlquery = "SELECT ".
4231
                        "DISTINCT agenda.*, ip.visibility, ip.to_group_id, ip.insert_user_id, ip.ref ".
4232
                        " FROM ".$t_a." agenda, ".
4233
                        $t_ip." ip ".
4234
                        " WHERE agenda.id = ip.ref ".
4235
                        " AND agenda.start_date>='$date_start' ".
4236
                        " AND agenda.end_date<='$date_end' ".
4237
                        " AND ip.tool='".TOOL_CALENDAR_EVENT."' ".
4238
                        " AND ( ip.to_user_id='".$user_id."' OR ip.to_group_id='0' OR ip.to_group_id IS NULL) ".
4239
                        " AND ip.visibility='1' ".
4240
                        " ORDER BY start_date ";
4241
                }
4242
            }
4243
4244
            $result = Database::query($sqlquery);
4245
            while ($item = Database::fetch_array($result)) {
4246
                $agendaday = date("j", strtotime($item['start_date']));
4247
                $month = date("n", strtotime($item['start_date']));
4248
                $year = date("Y", strtotime($item['start_date']));
4249
                $URL = api_get_path(
4250
                        WEB_PATH
4251
                    )."main/calendar/agenda.php?cidReq=".urlencode(
4252
                        $course["code"]
4253
                    )."&day=$agendaday&month=$month&year=$year#$agendaday";
4254
                list($year, $month, $day, $hour, $min, $sec) = explode(
4255
                    '[-: ]',
4256
                    $item['start_date']
4257
                );
4258
                $start_date = $year.$month.$day.$hour.$min;
4259
                list($year, $month, $day, $hour, $min, $sec) = explode(
4260
                    '[-: ]',
4261
                    $item['end_date']
4262
                );
4263
                $end_date = $year.$month.$day.$hour.$min;
4264
4265
                $items[] = [
4266
                    'datestart' => $start_date,
4267
                    'dateend' => $end_date,
4268
                    'title' => $item['title'],
4269
                    'link' => $URL,
4270
                    'coursetitle' => $c['name'],
4271
                ];
4272
            }
4273
        }
4274
4275
        return $items;
4276
    }
4277
4278
    /**
4279
     * This function calculates the startdate of the week (monday)
4280
     * and the enddate of the week (sunday)
4281
     * and returns it as an array.
4282
     */
4283
    public static function calculate_start_end_of_week($week_number, $year)
4284
    {
4285
        // determine the start and end date
4286
        // step 1: we calculate a timestamp for a day in this week
4287
        $random_day_in_week = mktime(
4288
                0,
4289
                0,
4290
                0,
4291
                1,
4292
                1,
4293
                $year
4294
            ) + ($week_number) * (7 * 24 * 60 * 60); // we calculate a random day in this week
4295
        // step 2: we which day this is (0=sunday, 1=monday, ...)
4296
        $number_day_in_week = date('w', $random_day_in_week);
4297
        // step 3: we calculate the timestamp of the monday of the week we are in
4298
        $start_timestamp = $random_day_in_week - (($number_day_in_week - 1) * 24 * 60 * 60);
4299
        // step 4: we calculate the timestamp of the sunday of the week we are in
4300
        $end_timestamp = $random_day_in_week + ((7 - $number_day_in_week + 1) * 24 * 60 * 60) - 3600;
4301
        // step 5: calculating the start_day, end_day, start_month, end_month, start_year, end_year
4302
        $start_day = date('j', $start_timestamp);
4303
        $start_month = date('n', $start_timestamp);
4304
        $start_year = date('Y', $start_timestamp);
4305
        $end_day = date('j', $end_timestamp);
4306
        $end_month = date('n', $end_timestamp);
4307
        $end_year = date('Y', $end_timestamp);
4308
        $start_end_array['start']['day'] = $start_day;
4309
        $start_end_array['start']['month'] = $start_month;
4310
        $start_end_array['start']['year'] = $start_year;
4311
        $start_end_array['end']['day'] = $end_day;
4312
        $start_end_array['end']['month'] = $end_month;
4313
        $start_end_array['end']['year'] = $end_year;
4314
4315
        return $start_end_array;
4316
    }
4317
4318
    /**
4319
     * @return bool
4320
     */
4321
    public function getIsAllowedToEdit()
4322
    {
4323
        return $this->isAllowedToEdit;
4324
    }
4325
4326
    /**
4327
     * @param bool $isAllowedToEdit
4328
     */
4329
    public function setIsAllowedToEdit($isAllowedToEdit)
4330
    {
4331
        $this->isAllowedToEdit = $isAllowedToEdit;
4332
    }
4333
4334
    /**
4335
     * Format needed for the Fullcalendar js lib.
4336
     *
4337
     * @param string $utcTime
4338
     *
4339
     * @return bool|string
4340
     */
4341
    public function formatEventDate($utcTime)
4342
    {
4343
        $utcTimeZone = new DateTimeZone('UTC');
4344
        $platformTimeZone = new DateTimeZone(api_get_timezone());
4345
4346
        $eventDate = new DateTime($utcTime, $utcTimeZone);
4347
        $eventDate->setTimezone($platformTimeZone);
4348
4349
        return $eventDate->format(DateTime::ISO8601);
4350
    }
4351
4352
    /**
4353
     * @throws \Doctrine\ORM\OptimisticLockException
4354
     * @throws \Doctrine\ORM\ORMException
4355
     * @throws \Doctrine\ORM\TransactionRequiredException
4356
     */
4357
    public static function saveCollectiveProperties(array $inviteeUserList, bool $isCollective, int $eventId)
4358
    {
4359
        $em = Database::getManager();
4360
4361
        $event = $em->find('ChamiloCoreBundle:PersonalAgenda', $eventId);
4362
4363
        $invitation = new AgendaEventInvitation();
4364
        $invitation->setCreator(api_get_user_entity(api_get_user_id()));
4365
4366
        $event
4367
            ->setCollective($isCollective)
4368
            ->setInvitation($invitation)
4369
        ;
4370
4371
        $em->persist($event);
4372
4373
        foreach ($inviteeUserList as $inviteeId) {
4374
            $invitee = new AgendaEventInvitee();
4375
            $invitee
4376
                ->setUser(api_get_user_entity($inviteeId))
4377
                ->setInvitation($invitation)
4378
            ;
4379
4380
            $em->persist($invitee);
4381
        }
4382
4383
        $em->flush();
4384
    }
4385
4386
    private static function isUserInvitedInEvent(int $id, int $userId): bool
4387
    {
4388
        $user = api_get_user_entity($userId);
4389
4390
        $event = Database::getManager()
4391
            ->getRepository('ChamiloCoreBundle:PersonalAgenda')
4392
            ->findOneByIdAndInvitee($id, $user)
4393
        ;
4394
4395
        return null !== $event;
4396
    }
4397
4398
    private function loadEventsAsInvitee(User $user, ?DateTime $startDate, ?DateTime $endDate)
4399
    {
4400
        $em = Database::getManager();
4401
        $eventRepo = $em->getRepository('ChamiloCoreBundle:PersonalAgenda');
4402
        $events = $eventRepo->getEventsForInvitee($user, $startDate, $endDate);
4403
4404
        foreach ($events as $event) {
4405
            $eventInfo = [];
4406
            $eventInfo['id'] = 'personal_'.$event->getId();
4407
            $eventInfo['title'] = $event->getTitle();
4408
            $eventInfo['className'] = 'personal';
4409
            $eventInfo['borderColor'] = $eventInfo['backgroundColor'] = $this->event_personal_color;
4410
            $eventInfo['editable'] = $event->isCollective();
4411
            $eventInfo['sent_to'] = get_lang('Me');
4412
            $eventInfo['type'] = 'personal';
4413
4414
            if ($event->getDate()) {
4415
                $eventInfo['start'] = $this->formatEventDate($event->getDate()->format('Y-m-d H:i:s'));
4416
                $eventInfo['start_date_localtime'] = api_get_local_time($event->getDate());
4417
            }
4418
4419
            if ($event->getEnddate()) {
4420
                $eventInfo['end'] = $this->formatEventDate($event->getEnddate()->format('Y-m-d H:i:s'));
4421
                $eventInfo['end_date_localtime'] = api_get_local_time($event->getEnddate());
4422
            }
4423
4424
            $eventInfo['description'] = $event->getText();
4425
            $eventInfo['allDay'] = $event->getAllDay();
4426
            $eventInfo['parent_event_id'] = 0;
4427
            $eventInfo['has_children'] = 0;
4428
            $eventInfo['collective'] = $event->isCollective();
4429
            $eventInfo['invitees'] = [];
4430
4431
            $invitation = $event->getInvitation();
4432
4433
            if ($invitation) {
4434
                foreach ($invitation->getInvitees() as $invitee) {
4435
                    $inviteeUser = $invitee->getUser();
4436
4437
                    $eventInfo['invitees'][] = [
4438
                        'id' => $inviteeUser->getId(),
4439
                        'name' => $inviteeUser->getCompleteNameWithUsername(),
4440
                    ];
4441
                }
4442
            }
4443
4444
            $this->events[] = $eventInfo;
4445
        }
4446
    }
4447
4448
    private function loadSessionsAsEvents(int $start, int $end)
4449
    {
4450
        if (false === api_get_configuration_value('personal_calendar_show_sessions_occupation')) {
4451
            return;
4452
        }
4453
4454
        $start = api_get_utc_datetime($start, false, true);
4455
        $end = api_get_utc_datetime($end, false, true);
4456
        $userInfo = api_get_user_info();
4457
        $sessionList = SessionManager::getSessionsFollowedByUser($userInfo['id'], $userInfo['status']);
4458
4459
        foreach ($sessionList as $sessionInfo) {
4460
            if (!empty($sessionInfo['duration'])) {
4461
                $courseAccess = CourseManager::getFirstCourseAccessPerSessionAndUser(
4462
                    $sessionInfo['session_id'],
4463
                    $userInfo['id']
4464
                );
4465
4466
                if (empty($courseAccess)) {
4467
                    continue;
4468
                }
4469
4470
                $firstAccessDate = new DateTime($courseAccess['login_course_date'], new DateTimeZone('UTC'));
4471
                $lastAccessDate = clone $firstAccessDate;
4472
                $lastAccessDate->modify('+'.$sessionInfo['duration'].' days');
4473
4474
                if ($firstAccessDate->format('Y-m-d H:i:s') > $start
4475
                    && $lastAccessDate->format('Y-m-d H:i:s') < $end
4476
                ) {
4477
                    continue;
4478
                }
4479
4480
                $courseList = SessionManager::get_course_list_by_session_id($sessionInfo['id']);
4481
                $firstCourse = current($courseList);
4482
4483
                $this->events[] = [
4484
                    'id' => 'session_'.$sessionInfo['id'],
4485
                    'session_id' => $sessionInfo['id'],
4486
                    'title' => $sessionInfo['name'],
4487
                    'description' => $sessionInfo['show_description'] ? $sessionInfo['description'] : '',
4488
                    'className' => 'personal',
4489
                    'borderColor' => $this->event_personal_color,
4490
                    'backgroundColor' => $this->event_personal_color,
4491
                    'editable' => false,
4492
                    'sent_to' => get_lang('Me'),
4493
                    'type' => 'session',
4494
                    'start' => $firstAccessDate->format(DateTime::ISO8601),
4495
                    'start_date_localtime' => api_get_local_time($firstAccessDate),
4496
                    'end' => $lastAccessDate->format(DateTime::ISO8601),
4497
                    'end_date_localtime' => api_get_local_time($lastAccessDate),
4498
                    'allDay' => 0,
4499
                    'parent_event_id' => 0,
4500
                    'has_children' => 0,
4501
                    'course_url' => api_get_course_url($firstCourse['code'], $sessionInfo['id']),
4502
                ];
4503
4504
                continue;
4505
            }
4506
4507
            if ($sessionInfo['display_start_date'] < $start
4508
                && $sessionInfo['display_end_date'] > $end
4509
            ) {
4510
                continue;
4511
            }
4512
4513
            $courseList = SessionManager::get_course_list_by_session_id($sessionInfo['id']);
4514
            $firstCourse = current($courseList);
4515
4516
            $this->events[] = [
4517
                'id' => 'session_'.$sessionInfo['id'],
4518
                'session_id' => $sessionInfo['id'],
4519
                'title' => $sessionInfo['name'],
4520
                'description' => $sessionInfo['show_description'] ? $sessionInfo['description'] : '',
4521
                'className' => 'personal',
4522
                'borderColor' => $this->event_personal_color,
4523
                'backgroundColor' => $this->event_personal_color,
4524
                'editable' => false,
4525
                'sent_to' => get_lang('Me'),
4526
                'type' => 'session',
4527
                'start' => $sessionInfo['display_start_date'],
4528
                'start_date_localtime' => $sessionInfo['display_start_date']
4529
                    ? $this->formatEventDate($sessionInfo['display_start_date'])
4530
                    : '',
4531
                'end' => $sessionInfo['display_end_date'],
4532
                'end_date_localtime' => $sessionInfo['display_end_date']
4533
                    ? $this->formatEventDate($sessionInfo['display_end_date'])
4534
                    : '',
4535
                'allDay' => 0,
4536
                'parent_event_id' => 0,
4537
                'has_children' => 0,
4538
                'course_url' => api_get_course_url($firstCourse['code'], $sessionInfo['id']),
4539
            ];
4540
        }
4541
    }
4542
}
4543