Completed
Push — 1.10.x ( 77bf11...88842f )
by Angel Fernando Quiroz
43:15
created

SessionManager   F

Complexity

Total Complexity 994

Size/Duplication

Total Lines 7831
Duplicated Lines 12.92 %

Coupling/Cohesion

Components 2
Dependencies 25

Importance

Changes 3
Bugs 1 Features 1
Metric Value
wmc 994
c 3
b 1
f 1
lcom 2
cbo 25
dl 1012
loc 7831
rs 0.5217

129 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 3 1
A fetch() 0 14 3
A session_name_exists() 0 9 1
C get_count_admin() 0 112 7
F get_sessions_admin() 47 156 34
A get_count_session_lp_progress() 0 21 1
F get_session_lp_progress() 0 116 13
F get_survey_overview() 0 101 13
F get_session_progress() 17 313 23
A get_number_of_tracking_access_overview() 0 7 1
F create_session() 27 177 31
A getCoachesByCourseSession() 22 22 3
A getCoachesByCourseSessionToString() 9 18 3
A getCoachesBySession() 0 19 3
A getAllCoursesFromAllSessionFromDrh() 0 14 4
F getAllUsersFromCoursesFromAllSessionFromStatus() 19 172 22
C updateCoaches() 0 33 7
C copyStudentsFromSession() 0 48 8
C copyCoachesFromSessionToCourse() 0 55 10
B getCountUserTracking() 0 52 5
D getTeacherTracking() 0 82 14
A getCourseToolToBeManaged() 0 7 1
A installCourse() 12 12 3
A unInstallCourse() 12 12 3
A addCourseIntroduction() 0 19 3
A removeCourseIntroduction() 0 9 1
A addCourseDescription() 0 7 1
A removeCourseDescription() 0 4 1
A subscribeDrhToSessionList() 0 18 4
C checkSubscribeDrhToSessionList() 0 41 11
B importSessionDrhCSV() 0 23 5
F get_user_data_access_tracking_overview() 0 136 20
B generateNextSessionName() 22 22 4
F edit_session() 0 115 22
C move() 0 63 9
A moveUp() 0 4 1
A moveDown() 0 4 1
A durationPerUserIsEnabled() 0 4 1
A getDayLeftInSession() 0 23 2
A editUserSessionDuration() 0 15 3
A getUserSession() 0 20 4
A isUserSubscribedAsStudent() 0 23 3
D getSessionsCoachedByUser() 0 45 10
B sessionHasCourse() 0 27 3
B getAllCourseCoaches() 0 38 4
B getTotalUserTimeInPlatform() 4 29 5
A getCoursesListByCourseCoach() 0 12 1
A getTotalUserCoursesInSession() 0 19 2
D getShortSessionListAndExtraByCategory() 0 94 13
C getSessionCategoryIdByName() 0 37 7
D getSessionListAndExtraByCategoryId() 0 128 15
B getDescriptionFromSessionId() 0 27 3
B searchSession() 0 38 4
B getFilteredExtraFields() 0 54 6
A isValidId() 0 17 3
B getSessionsFollowedForGroupAdmin() 46 46 5
A getSessionVisibility() 0 11 4
C convertSessionDateToString() 0 30 8
B parseSessionDates() 0 25 1
C delete() 0 69 7
A clear_session_ref_promotion() 12 12 2
F suscribe_users_to_session() 48 217 25
B getUsersByCourseSession() 4 36 6
B removeUsersFromCourseSession() 4 55 9
D subscribe_users_to_session_course() 10 107 12
A unsubscribe_user_from_session() 0 56 4
D add_courses_to_session() 20 188 20
A unsubscribe_course_from_session() 0 47 3
A create_session_extra_field() 11 11 1
A update_session_extra_field_value() 10 10 1
A relation_session_course_exist() 15 15 2
A get_session_by_name() 0 19 3
C create_category_session() 15 57 18
C edit_category_session() 15 54 20
B delete_session_category() 0 42 5
D get_sessions_list() 0 85 15
A get_session_category() 0 15 2
A get_all_session_category() 0 15 2
C set_coach_to_course_session() 52 110 11
C suscribe_sessions_to_hr_manager() 10 79 11
A getDrhUsersInSession() 0 4 1
B getSessionFollowedByDrh() 0 41 3
B get_sessions_followed_by_drh() 0 24 1
F getSessionsFollowedByUser() 12 139 15
B get_course_list_by_session_id() 11 58 8
C getAllCoursesFollowedByUser() 5 71 9
B get_course_list_by_session_id_like() 0 34 5
B getCourseCountBySessionId() 0 29 3
A getSessionIdFromOriginalId() 0 14 2
B get_users_by_session() 0 45 6
B get_sessions_by_general_coach() 0 34 5
A get_sessions_by_coach() 0 5 1
A get_user_status_in_course_session() 21 21 2
B get_user_status_in_session() 0 21 5
A get_all_sessions_by_promotion() 0 5 1
A suscribe_sessions_to_promotion() 0 15 3
A set_session_status() 0 6 1
F copy() 0 145 26
A user_is_general_coach() 0 14 3
A count_sessions() 0 13 3
B protectSession() 0 20 5
D allowed() 0 32 9
A allowToManageSessions() 0 15 4
A allowOnlyMySessions() 0 11 4
A allowManageAllSessions() 0 8 2
A protect_teacher_session_edit() 0 8 3
A get_session_by_course() 0 13 1
B get_sessions_by_user() 0 21 5
D importCSV() 301 778 149
A orderCourseIsEnabled() 0 9 2
D setForm() 21 245 10
C get_count_admin_complete() 26 93 10
B getGridColumns() 0 75 4
F convert_dates_to_local() 18 42 11
F get_sessions_admin_complete() 104 237 35
B compareArraysToMerge() 0 15 6
A getAdminPath() 0 9 2
A getPath() 0 18 4
B getSessionCourseForUser() 0 26 5
B getCoursesForCourseSessionCoach() 0 27 4
B isSessionDateOkForCoach() 0 34 1
B getCoursesForMainSessionCoach() 0 25 5
A getCoursesInSession() 0 19 2
B getNamedSessionCourseForCoach() 0 68 6
A compareCatSessionInfo() 10 10 3
B compareBySessionName() 0 14 5
A compareByUserCourseCat() 10 10 3
A compareByCourse() 10 10 3
B getHtmlNamedSessionCourseForCoach() 0 66 5

How to fix   Duplicated Code    Complexity   

Duplicated Code

Duplicate code is one of the most pungent code smells. A rule that is often used is to re-structure code once it is duplicated in three or more places.

Common duplication problems, and corresponding solutions are:

Complex Class

 Tip:   Before tackling complexity, make sure that you eliminate any duplication first. This often can reduce the size of classes significantly.

Complex classes like SessionManager often do a lot of different things. To break such a class down, we need to identify a cohesive component within that class. A common approach to find such a component is to look for fields/methods that share the same prefixes, or suffixes. You can also have a look at the cohesion graph to spot any un-connected, or weakly-connected components.

Once you have determined the fields that belong together, you can apply the Extract Class refactoring. If the component makes sense as a sub-class, Extract Subclass is also a candidate, and is often faster.

While breaking up the class, it is a good idea to analyze how other classes use SessionManager, and based on these observations, apply Extract Interface, too.

1
<?php
2
/* For licensing terms, see /license.txt */
3
4
use Chamilo\CoreBundle\Entity\SessionRelCourseRelUser;
5
6
/**
7
 * Class SessionManager
8
 *
9
 * This is the session library for Chamilo.
10
 * All main sessions functions should be placed here.
11
 * This class provides methods for sessions management.
12
 * Include/require it in your code to use its features.
13
 *
14
 * @package chamilo.library
15
 *
16
 */
17
class SessionManager
18
{
19
    public static $_debug = false;
20
21
    /**
22
     * Constructor
23
     */
24
    public function __construct()
25
    {
26
    }
27
28
    /**
29
     * Fetches a session from the database
30
     * @param  int $id Session Id
31
     *
32
     * @return  array   Session details
33
     */
34
    public static function fetch($id)
35
    {
36
        $t = Database::get_main_table(TABLE_MAIN_SESSION);
37
        if ($id != strval(intval($id))) {
38
            return array();
39
        }
40
        $s = "SELECT * FROM $t WHERE id = $id";
41
        $r = Database::query($s);
42
        if (Database::num_rows($r) != 1) {
43
            return array();
44
        }
45
46
        return Database::fetch_array($r, 'ASSOC');
47
    }
48
49
    /**
50
     * Create a session
51
     * @author Carlos Vargas <[email protected]>, from existing code
52
     * @param   string  $name
53
     * @param   string  $startDate (YYYY-MM-DD hh:mm:ss)
54
     * @param   string  $endDate (YYYY-MM-DD hh:mm:ss)
55
     * @param   string  $displayStartDate (YYYY-MM-DD hh:mm:ss)
56
     * @param   string  $displayEndDate (YYYY-MM-DD hh:mm:ss)
57
     * @param   string  $coachStartDate (YYYY-MM-DD hh:mm:ss)
58
     * @param   string  $coachEndDate (YYYY-MM-DD hh:mm:ss)
59
     * @param   mixed   $coachId If integer, this is the session coach id, if string, the coach ID will be looked for from the user table
60
     * @param   integer $sessionCategoryId ID of the session category in which this session is registered
61
     * @param   integer $visibility Visibility after end date (0 = read-only, 1 = invisible, 2 = accessible)
62
     * @param   bool    $fixSessionNameIfExists
63
     * @param   string  $duration
64
     * @param   string  $description Optional. The session description
65
     * @param   int     $showDescription Optional. Whether show the session description
66
     * @param   array   $extraFields
67
     * @param   int     $sessionAdminId Optional. If this sessions was created by a session admin, assign it to him
68
     * @param boolean $sendSubscritionNotification Optional.
69
     *          Whether send a mail notification to users being subscribed
70
     * @todo use an array to replace all this parameters or use the model.lib.php ...
71
     * @return mixed       Session ID on success, error message otherwise
72
     * */
73
    public static function create_session(
74
        $name,
75
        $startDate,
76
        $endDate,
77
        $displayStartDate,
78
        $displayEndDate,
79
        $coachStartDate,
80
        $coachEndDate,
81
        $coachId,
82
        $sessionCategoryId,
83
        $visibility = 1,
84
        $fixSessionNameIfExists = false,
85
        $duration = null,
86
        $description = null,
87
        $showDescription = 0,
88
        $extraFields = array(),
89
        $sessionAdminId = 0,
90
        $sendSubscritionNotification = false
91
    ) {
92
        global $_configuration;
93
94
        //Check portal limits
95
        $access_url_id = 1;
96
97
        if (api_get_multiple_access_url()) {
98
            $access_url_id = api_get_current_access_url_id();
99
        }
100
101 View Code Duplication
        if (is_array($_configuration[$access_url_id]) &&
102
            isset($_configuration[$access_url_id]['hosting_limit_sessions']) &&
103
            $_configuration[$access_url_id]['hosting_limit_sessions'] > 0
104
        ) {
105
            $num = self::count_sessions();
106
            if ($num >= $_configuration[$access_url_id]['hosting_limit_sessions']) {
107
                api_warn_hosting_contact('hosting_limit_sessions');
108
                return get_lang('PortalSessionsLimitReached');
109
            }
110
        }
111
112
        $name = Database::escape_string(trim($name));
113
        $sessionCategoryId = intval($sessionCategoryId);
114
        $visibility = intval($visibility);
115
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
116
117
        $startDate = Database::escape_string($startDate);
118
        $endDate = Database::escape_string($endDate);
119
120
        if (empty($name)) {
121
            $msg = get_lang('SessionNameIsRequired');
122
            return $msg;
123
        } elseif (empty($coachId)) {
124
            $msg = get_lang('CoachIsRequired');
125
            return $msg;
126
        } elseif (!empty($startDate) && !api_is_valid_date($startDate, 'Y-m-d H:i') && !api_is_valid_date($startDate, 'Y-m-d H:i:s')) {
127
            $msg = get_lang('InvalidStartDate');
128
            return $msg;
129
        } elseif (!empty($endDate) && !api_is_valid_date($endDate, 'Y-m-d H:i') && !api_is_valid_date($endDate, 'Y-m-d H:i:s')) {
130
            $msg = get_lang('InvalidEndDate');
131
            return $msg;
132
        } elseif (!empty($startDate) && !empty($endDate) && $startDate >= $endDate) {
133
            $msg = get_lang('StartDateShouldBeBeforeEndDate');
134
            return $msg;
135
        } else {
136
            $ready_to_create = false;
137
            if ($fixSessionNameIfExists) {
138
                $name = self::generateNextSessionName($name);
139
                if ($name) {
140
                    $ready_to_create = true;
141
                } else {
142
                    $msg = get_lang('SessionNameAlreadyExists');
143
                    return $msg;
144
                }
145
            } else {
146
                $rs = Database::query("SELECT 1 FROM $tbl_session WHERE name='" . $name . "'");
147
                if (Database::num_rows($rs)) {
148
                    $msg = get_lang('SessionNameAlreadyExists');
149
                    return $msg;
150
                }
151
                $ready_to_create = true;
152
            }
153
154
            if ($ready_to_create) {
155
                $sessionAdminId = !empty($sessionAdminId) ? $sessionAdminId : api_get_user_id();
156
                $values = array(
157
                    'name' => $name,
158
                    'id_coach' => $coachId,
159
                    'session_admin_id' => $sessionAdminId,
160
                    'visibility' => $visibility,
161
                    'description' => $description,
162
                    'show_description' => intval($showDescription),
163
                    'send_subscription_notification' => $sendSubscritionNotification
164
                );
165
166
                if (!empty($startDate)) {
167
                    $values['access_start_date'] = api_get_utc_datetime($startDate);
168
                }
169
170
                if (!empty($endDate)) {
171
                    $values['access_end_date'] = api_get_utc_datetime($endDate);
172
                }
173
174
                if (!empty($displayStartDate)) {
175
                    $values['display_start_date'] = api_get_utc_datetime($displayStartDate);
176
                }
177
178
                if (!empty($displayEndDate)) {
179
                    $values['display_end_date'] = api_get_utc_datetime($displayEndDate);
180
                }
181
182
                if (!empty($coachStartDate)) {
183
                    $values['coach_access_start_date'] = api_get_utc_datetime($coachStartDate);
184
                }
185
                if (!empty($coachEndDate)) {
186
                    $values['coach_access_end_date'] = api_get_utc_datetime($coachEndDate);
187
                }
188
189
                if (!empty($sessionCategoryId)) {
190
                    $values['session_category_id'] = $sessionCategoryId;
191
                }
192
193
                $session_id = Database::insert($tbl_session, $values);
194
195
                $duration = intval($duration);
196
197 View Code Duplication
                if (!empty($duration)) {
198
                    $sql = "UPDATE $tbl_session SET
199
                        access_start_date = NULL,
200
                        access_end_date = NULL,
201
                        display_start_date = NULL,
202
                        display_end_date = NULL,
203
                        coach_access_start_date = NULL,
204
                        coach_access_end_date = NULL,
205
                        duration = $duration
206
                    WHERE id = $session_id";
207
                    Database::query($sql);
208
                } else {
209
                    $sql = "UPDATE $tbl_session
210
                        SET duration = 0
211
                        WHERE id = $session_id";
212
                    Database::query($sql);
213
                }
214
215
                if (!empty($session_id)) {
216
                    $extraFields['item_id'] = $session_id;
217
218
                    $sessionFieldValue = new ExtraFieldValue('session');
219
                    $sessionFieldValue->saveFieldValues($extraFields);
220
221
                    /*
222
                      Sends a message to the user_id = 1
223
224
                      $user_info = api_get_user_info(1);
225
                      $complete_name = $user_info['firstname'].' '.$user_info['lastname'];
226
                      $subject = api_get_setting('siteName').' - '.get_lang('ANewSessionWasCreated');
227
                      $message = get_lang('ANewSessionWasCreated')." <br /> ".get_lang('NameOfTheSession').' : '.$name;
228
                      api_mail_html($complete_name, $user_info['email'], $subject, $message);
229
                     *
230
                     */
231
                    //Adding to the correct URL
232
                    $access_url_id = api_get_current_access_url_id();
233
                    UrlManager::add_session_to_url($session_id, $access_url_id);
234
235
                    // add event to system log
236
                    $user_id = api_get_user_id();
237
                    Event::addEvent(
238
                        LOG_SESSION_CREATE,
239
                        LOG_SESSION_ID,
240
                        $session_id,
241
                        api_get_utc_datetime(),
242
                        $user_id
243
                    );
244
                }
245
246
                return $session_id;
247
            }
248
        }
249
    }
250
251
    /**
252
     * @param string $name
253
     *
254
     * @return bool
255
     */
256
    public static function session_name_exists($name)
257
    {
258
        $name = Database::escape_string($name);
259
        $sql = "SELECT COUNT(*) as count FROM " . Database::get_main_table(TABLE_MAIN_SESSION) . "
260
                WHERE name = '$name'";
261
        $result = Database::fetch_array(Database::query($sql));
0 ignored issues
show
Bug introduced by
It seems like \Database::query($sql) can be null; however, fetch_array() does not accept null, maybe add an additional type check?

Unless you are absolutely sure that the expression can never be null because of other conditions, we strongly recommend to add an additional type check to your code:

/** @return stdClass|null */
function mayReturnNull() { }

function doesNotAcceptNull(stdClass $x) { }

// With potential error.
function withoutCheck() {
    $x = mayReturnNull();
    doesNotAcceptNull($x); // Potential error here.
}

// Safe - Alternative 1
function withCheck1() {
    $x = mayReturnNull();
    if ( ! $x instanceof stdClass) {
        throw new \LogicException('$x must be defined.');
    }
    doesNotAcceptNull($x);
}

// Safe - Alternative 2
function withCheck2() {
    $x = mayReturnNull();
    if ($x instanceof stdClass) {
        doesNotAcceptNull($x);
    }
}
Loading history...
262
263
        return $result['count'] > 0;
264
    }
265
266
    /**
267
     * @param string $where_condition
268
     *
269
     * @return mixed
270
     */
271
    public static function get_count_admin($where_condition = '')
272
    {
273
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
274
        $tbl_session_category = Database::get_main_table(TABLE_MAIN_SESSION_CATEGORY);
275
        $tbl_user = Database::get_main_table(TABLE_MAIN_USER);
276
        $table_access_url_rel_session = Database::get_main_table(TABLE_MAIN_ACCESS_URL_REL_SESSION);
277
        $tbl_session_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_USER);
278
279
        $where = 'WHERE 1=1 ';
280
        $user_id = api_get_user_id();
281
282
        $extraJoin = '';
283
284
        if (api_is_session_admin() &&
285
            api_get_setting('allow_session_admins_to_manage_all_sessions') == 'false'
286
        ) {
287
            $where .= " AND (
288
                            s.session_admin_id = $user_id  OR
289
                            sru.user_id = '$user_id' AND
290
                            sru.relation_type = '" . SESSION_RELATION_TYPE_RRHH . "'
291
                            )
292
                      ";
293
294
            $extraJoin = " INNER JOIN $tbl_session_rel_user sru
295
                           ON sru.session_id = s.id ";
296
        }
297
298
        $today = api_get_utc_datetime();
299
        $today = api_strtotime($today, 'UTC');
300
        $today = date('Y-m-d', $today);
301
302
        if (!empty($where_condition)) {
303
            $where_condition = str_replace("(  session_active = ':'  )", '1=1', $where_condition);
304
305
            $where_condition = str_replace('category_name', 'sc.name', $where_condition);
306
            $where_condition = str_replace(
307
                array("AND session_active = '1'  )", " AND (  session_active = '1'  )"),
308
                array(') GROUP BY s.name HAVING session_active = 1 ', " GROUP BY s.name HAVING session_active = 1 " )
309
                , $where_condition
310
            );
311
            $where_condition = str_replace(
312
                array("AND session_active = '0'  )", " AND (  session_active = '0'  )"),
313
                array(') GROUP BY s.name HAVING session_active = 0 ', " GROUP BY s.name HAVING session_active = '0' "),
314
                $where_condition
315
            );
316
        } else {
317
            $where_condition = " AND 1 = 1";
318
        }
319
320
        $courseCondition = null;
321
        if (strpos($where_condition, 'c.id')) {
322
            $table = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
323
            $tableCourse = Database::get_main_table(TABLE_MAIN_COURSE);
324
            $courseCondition = " INNER JOIN $table course_rel_session
325
                                 ON (s.id = course_rel_session.session_id)
326
                                 INNER JOIN $tableCourse c
327
                                 ON (course_rel_session.c_id = c.id)
328
                                ";
329
        }
330
331
        $sql = "SELECT COUNT(id) as total_rows FROM (
332
                SELECT DISTINCT
333
                 IF (
334
					(s.access_start_date <= '$today' AND '$today' <= s.access_end_date) OR
335
                    (s.access_start_date IS NULL AND s.access_end_date  = IS NULL ) OR
336
					(s.access_start_date <= '$today' AND s.access_end_date IS NULL) OR
337
					('$today' <= s.access_end_date AND s.access_start_date IS NULL)
338
				, 1, 0) as session_active,
339
                s.id
340
                FROM $tbl_session s
341
                LEFT JOIN $tbl_session_category sc
342
                ON s.session_category_id = sc.id
343
                INNER JOIN $tbl_user u
344
                ON s.id_coach = u.user_id
345
                $courseCondition
346
                $extraJoin
347
                $where $where_condition ) as session_table";
348
349
        if (api_is_multiple_url_enabled()) {
350
351
            $access_url_id = api_get_current_access_url_id();
352
            if ($access_url_id != -1) {
353
                $where.= " AND ar.access_url_id = $access_url_id ";
354
355
                $sql = "SELECT count(id) as total_rows FROM (
356
                SELECT DISTINCT
357
                  IF (
358
					(s.access_start_date <= '$today' AND '$today' <= s.access_end_date) OR
359
                    (s.access_start_date IS NULL AND s.access_end_date IS NULL) OR
360
					(s.access_start_date <= '$today' AND s.access_end_date IS NULL) OR
361
					('$today' <= s.access_end_date AND s.access_start_date IS NULL)
362
				, 1, 0)
363
				as session_active,
364
				s.id
365
                FROM $tbl_session s
366
                    LEFT JOIN  $tbl_session_category sc
367
                    ON s.session_category_id = sc.id
368
                    INNER JOIN $tbl_user u ON s.id_coach = u.user_id
369
                    INNER JOIN $table_access_url_rel_session ar
370
                    ON ar.session_id = s.id
371
                    $courseCondition
372
                    $extraJoin
373
                $where $where_condition) as session_table";
374
            }
375
        }
376
377
        $result_rows = Database::query($sql);
378
        $row = Database::fetch_array($result_rows);
379
        $num = $row['total_rows'];
380
381
        return $num;
382
    }
383
384
    /**
385
     * Gets the admin session list callback of the session/session_list.php page
386
     * @param array $options order and limit keys
387
     * @param boolean $get_count Whether to get all the results or only the count
388
     * @return mixed Integer for number of rows, or array of results
389
     * @assert (array(),true) !== false
390
     */
391
    public static function get_sessions_admin($options = array(), $get_count = false)
392
    {
393
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
394
        $sessionCategoryTable = Database::get_main_table(TABLE_MAIN_SESSION_CATEGORY);
395
396
        $where = 'WHERE 1 = 1 ';
397
        $user_id = api_get_user_id();
398
399 View Code Duplication
        if (!api_is_platform_admin()) {
400
            if (api_is_session_admin() &&
401
                api_get_setting('allow_session_admins_to_manage_all_sessions') == 'false'
402
            ) {
403
                $where .=" AND s.session_admin_id = $user_id ";
404
            }
405
        }
406
407
        if (!api_is_platform_admin() && api_is_teacher() &&
408
            api_get_setting('allow_teachers_to_create_sessions') == 'true'
409
        ) {
410
            $where .=" AND s.id_coach = $user_id ";
411
        }
412
413
        $extra_field = new ExtraField('session');
414
        $conditions = $extra_field->parseConditions($options);
415
        $inject_joins = $conditions['inject_joins'];
416
        $where .= $conditions['where'];
417
        $inject_where = $conditions['inject_where'];
418
        $inject_extra_fields = $conditions['inject_extra_fields'];
419
420
        $order = $conditions['order'];
421
        $limit = $conditions['limit'];
422
423
        $isMakingOrder = false;
424
425
        if ($get_count == true) {
426
            $select = " SELECT count(*) as total_rows";
427
        } else {
428
            $select =
429
                "SELECT DISTINCT ".
430
                " s.name, ".
431
                " s.display_start_date, ".
432
                " s.display_end_date, ".
433
                " access_start_date, ".
434
                " access_end_date, ".
435
                " s.visibility, ".
436
                " s.session_category_id, ".
437
                " $inject_extra_fields ".
438
                " s.id ";
439
440
            $isMakingOrder = strpos($options['order'], 'category_name') === 0;
441
        }
442
443
        $isFilteringSessionCategory = strpos($where, 'category_name') !== false;
444
445
        if ($isMakingOrder || $isFilteringSessionCategory) {
446
            $inject_joins .= " LEFT JOIN $sessionCategoryTable sc ON s.session_category_id = sc.id ";
447
448
            if ($isFilteringSessionCategory) {
449
                $where = str_replace('category_name', 'sc.name', $where);
450
            }
451
452
            if ($isMakingOrder) {
453
                $order = str_replace('category_name', 'sc.name', $order);
454
            }
455
        }
456
457
        $query = "$select FROM $tbl_session s $inject_joins $where $inject_where";
458
459
        if (api_is_multiple_url_enabled()) {
460
            $table_access_url_rel_session= Database::get_main_table(TABLE_MAIN_ACCESS_URL_REL_SESSION);
461
            $access_url_id = api_get_current_access_url_id();
462
            if ($access_url_id != -1) {
463
                $where.= " AND ar.access_url_id = $access_url_id ";
464
                $query = "$select
465
                        FROM $tbl_session s $inject_joins
466
                        INNER JOIN $table_access_url_rel_session ar
467
                        ON (ar.session_id = s.id) $where";
468
            }
469
        }
470
471
        $query .= $order;
472
        $query .= $limit;
473
        $result = Database::query($query);
474
475
        $categories = self::get_all_session_category();
476
        $orderedCategories = array();
477
        if (!empty($categories)) {
478
            foreach ($categories as $category) {
479
                $orderedCategories[$category['id']] = $category['name'];
480
            }
481
        }
482
483
        $formatted_sessions = array();
484
485
        if (Database::num_rows($result)) {
486
            $sessions = Database::store_result($result, 'ASSOC');
487
            if ($get_count) {
488
                return $sessions[0]['total_rows'];
489
            }
490
491
            foreach ($sessions as $session) {
492
                $session_id = $session['id'];
493
                $session['name'] = Display::url($session['name'], "resume_session.php?id_session=".$session['id']);
494
495 View Code Duplication
                if (isset($session['session_active']) && $session['session_active'] == 1) {
496
                    $session['session_active'] = Display::return_icon('accept.png', get_lang('Active'), array(), ICON_SIZE_SMALL);
497
                } else {
498
                    $session['session_active'] = Display::return_icon('error.png', get_lang('Inactive'), array(), ICON_SIZE_SMALL);
499
                }
500
501
                $session = self::convert_dates_to_local($session, true);
502
503 View Code Duplication
                switch ($session['visibility']) {
504
                    case SESSION_VISIBLE_READ_ONLY: //1
505
                        $session['visibility'] = get_lang('ReadOnly');
506
                        break;
507
                    case SESSION_VISIBLE:           //2
508
                    case SESSION_AVAILABLE:         //4
509
                        $session['visibility'] = get_lang('Visible');
510
                        break;
511
                    case SESSION_INVISIBLE:         //3
512
                        $session['visibility'] = api_ucfirst(get_lang('Invisible'));
513
                        break;
514
                }
515
516
                // Cleaning double selects.
517 View Code Duplication
                foreach ($session as $key => &$value) {
0 ignored issues
show
Bug introduced by
The expression $session of type false|array<string,strin...d_date":"string|null"}> is not guaranteed to be traversable. How about adding an additional type check?

There are different options of fixing this problem.

  1. If you want to be on the safe side, you can add an additional type-check:

    $collection = json_decode($data, true);
    if ( ! is_array($collection)) {
        throw new \RuntimeException('$collection must be an array.');
    }
    
    foreach ($collection as $item) { /** ... */ }
    
  2. If you are sure that the expression is traversable, you might want to add a doc comment cast to improve IDE auto-completion and static analysis:

    /** @var array $collection */
    $collection = json_decode($data, true);
    
    foreach ($collection as $item) { /** .. */ }
    
  3. Mark the issue as a false-positive: Just hover the remove button, in the top-right corner of this issue for more options.

Loading history...
518
                    if (isset($options_by_double[$key]) || isset($options_by_double[$key.'_second'])) {
519
                        $options = explode('::', $value);
520
                    }
521
                    $original_key = $key;
522
523
                    if (strpos($key, '_second') === false) {
0 ignored issues
show
Unused Code introduced by
This if statement is empty and can be removed.

This check looks for the bodies of if statements that have no statements or where all statements have been commented out. This may be the result of changes for debugging or the code may simply be obsolete.

These if bodies can be removed. If you have an empty if but statements in the else branch, consider inverting the condition.

if (rand(1, 6) > 3) {
//print "Check failed";
} else {
    print "Check succeeded";
}

could be turned into

if (rand(1, 6) <= 3) {
    print "Check succeeded";
}

This is much more concise to read.

Loading history...
524
                    } else {
525
                        $key = str_replace('_second', '', $key);
526
                    }
527
528
                    if (isset($options_by_double[$key])) {
529
                        if (isset($options[0])) {
530
                            if (isset($options_by_double[$key][$options[0]])) {
531
                                if (strpos($original_key, '_second') === false) {
532
                                    $value = $options_by_double[$key][$options[0]]['option_display_text'];
533
                                } else {
534
                                    $value = $options_by_double[$key][$options[1]]['option_display_text'];
535
                                }
536
                            }
537
                        }
538
                    }
539
                }
540
                $formatted_sessions[$session_id] = $session;
541
                $categoryName = isset($orderedCategories[$session['session_category_id']]) ? $orderedCategories[$session['session_category_id']] : '';
542
                $formatted_sessions[$session_id]['category_name'] = $categoryName;
543
            }
544
        }
545
        return $formatted_sessions;
546
    }
547
548
    /**
549
     *  Get total of records for progress of learning paths in the given session
550
     *  @param int session id
551
     *  @return int
552
     */
553
    public static function get_count_session_lp_progress($sessionId = 0)
554
    {
555
        $tbl_lp = Database::get_course_table(TABLE_LP_MAIN);
556
        $tbl_lp_view = Database::get_course_table(TABLE_LP_VIEW);
557
        $tbl_user = Database::get_main_table(TABLE_MAIN_USER);
558
        $tbl_course = Database::get_main_table(TABLE_MAIN_COURSE);
559
560
        $sessionId = intval($sessionId);
561
562
        $sql = "SELECT  count(*) as total_rows
563
                FROM $tbl_lp_view v
564
                INNER JOIN $tbl_lp l ON l.id = v.lp_id
565
                INNER JOIN $tbl_user u ON u.user_id = v.user_id
566
                INNER JOIN $tbl_course c
567
                WHERE v.session_id = " . $sessionId;
568
        $result_rows = Database::query($sql);
569
        $row = Database::fetch_array($result_rows);
570
        $num = $row['total_rows'];
571
572
        return $num;
573
    }
574
575
    /**
576
     * Gets the progress of learning paths in the given session
577
     * @param int   $sessionId
578
     * @param int $courseId
579
     * @param string $date_from
580
     * @param string $date_to
581
     * @param array options order and limit keys
582
     * @return array table with user name, lp name, progress
583
     */
584
    public static function get_session_lp_progress($sessionId = 0, $courseId = 0, $date_from, $date_to, $options)
585
    {
586
        //escaping vars
587
        $sessionId = $sessionId == 'T' ? 'T' : intval($sessionId);
588
        $courseId = intval($courseId);
589
        $date_from = Database :: escape_string($date_from);
590
        $date_to = Database :: escape_string($date_to);
591
592
        //tables
593
        $session_course_user = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
594
        $user = Database::get_main_table(TABLE_MAIN_USER);
595
        $tbl_course_lp_view = Database::get_course_table(TABLE_LP_VIEW);
596
597
        $course = api_get_course_info_by_id($courseId);
598
599
        //getting all the students of the course
600
        //we are not using this because it only returns user ids
601
        /* if (empty($sessionId)
602
          {
603
          // Registered students in a course outside session.
604
          $users = CourseManager :: get_student_list_from_course_code($course_code);
605
          } else {
606
          // Registered students in session.
607
          $users = CourseManager :: get_student_list_from_course_code($course_code, true, $sessionId);
608
          } */
609
610
        $sessionCond = 'and session_id = %s';
611
        if ($sessionId == 'T') {
612
            $sessionCond = "";
613
        }
614
615
        $where = " WHERE c_id = '%s' AND s.status <> 2 $sessionCond";
616
617
        $limit = null;
618
        if (!empty($options['limit'])) {
619
            $limit = " LIMIT " . $options['limit'];
620
        }
621
622
        if (!empty($options['where'])) {
623
            $where .= ' '.$options['where'];
624
        }
625
626
        $order = null;
627
        if (!empty($options['order'])) {
628
            $order = " ORDER BY " . $options['order'];
629
        }
630
631
        $sql = "SELECT u.user_id, u.lastname, u.firstname, u.username, u.email, s.c_id
632
                FROM $session_course_user s
633
                INNER JOIN $user u ON u.user_id = s.user_id
634
                $where
635
                $order
636
                $limit";
637
638
        $sql_query = sprintf($sql, Database::escape_string($course['real_id']), $sessionId);
639
640
        $rs = Database::query($sql_query);
641
        while ($user = Database::fetch_array($rs)) {
642
            $users[$user['user_id']] = $user;
643
        }
644
645
        //Get lessons
646
        $lessons = LearnpathList::get_course_lessons($course['code'], $sessionId);
647
648
        $table = array();
649
        foreach ($users as $user) {
650
            $data = array(
651
                'lastname' => $user[1],
652
                'firstname' => $user[2],
653
                'username' => $user[3],
654
            );
655
656
            $sessionCond = 'AND v.session_id = %d';
657
            if ($sessionId == 'T') {
658
                $sessionCond = "";
659
            }
660
661
            //Get lessons progress by user
662
            $sql = "SELECT v.lp_id as id, v.progress
663
                    FROM  $tbl_course_lp_view v
664
                    WHERE v.c_id = %d
665
                    AND v.user_id = %d
666
            $sessionCond";
667
668
            $sql_query = sprintf($sql,
669
                intval($courseId),
670
                intval($user['user_id']),
671
                $sessionId
672
            );
673
674
            $result = Database::query($sql_query);
675
676
            $user_lessons = array();
677
            while ($row = Database::fetch_array($result)) {
678
                $user_lessons[$row['id']] = $row;
679
            }
680
681
            //Match course lessons with user progress
682
            $progress = 0;
683
            $count = 0;
684
            foreach ($lessons as $lesson) {
685
                $data[$lesson['id']] = (!empty($user_lessons[$lesson['id']]['progress'])) ? $user_lessons[$lesson['id']]['progress'] : 0;
686
                $progress += $data[$lesson['id']];
687
                $data[$lesson['id']] = $data[$lesson['id']] . '%';
688
                $count++;
689
            }
690
            if ($count == 0) {
691
                $data['total'] = 0;
692
            } else {
693
                $data['total'] = round($progress / $count, 2) . '%';
694
            }
695
            $table[] = $data;
696
        }
697
698
        return $table;
699
    }
700
701
    /**
702
     * Gets the survey answers
703
     * @param int   $sessionId
704
     * @param int   $courseId
705
     * @param int   $surveyId
706
     * @param array options order and limit keys
707
     * @todo fix the query
708
     * @return array table with user name, lp name, progress
709
     */
710
    public static function get_survey_overview($sessionId = 0, $courseId = 0, $surveyId = 0, $date_from, $date_to, $options)
711
    {
712
        //escaping vars
713
        $sessionId = intval($sessionId);
714
        $courseId = intval($courseId);
715
        $surveyId = intval($surveyId);
716
        $date_from = Database::escape_string($date_from);
717
        $date_to = Database::escape_string($date_to);
718
719
        //tables
720
        $session_course_user = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
721
        $user = Database::get_main_table(TABLE_MAIN_USER);
722
        $tbl_course_lp_view = Database::get_course_table(TABLE_LP_VIEW);
723
        $c_survey = Database::get_course_table(TABLE_SURVEY);
724
        $c_survey_answer = Database::get_course_table(TABLE_SURVEY_ANSWER);
725
        $c_survey_question = Database::get_course_table(TABLE_SURVEY_QUESTION);
726
        $c_survey_question_option = Database::get_course_table(TABLE_SURVEY_QUESTION_OPTION);
727
728
        $course = api_get_course_info_by_id($courseId);
729
730
        $where = " WHERE c_id = '%s' AND s.status <> 2 AND session_id = %s";
731
732
        $limit = null;
733
        if (!empty($options['limit'])) {
734
            $limit = " LIMIT " . $options['limit'];
735
        }
736
737
        if (!empty($options['where'])) {
738
            $where .= ' '.$options['where'];
739
        }
740
741
        $order = null;
742
        if (!empty($options['order'])) {
743
            $order = " ORDER BY " . $options['order'];
744
        }
745
746
        $sql = "SELECT u.user_id, u.lastname, u.firstname, u.username, u.email, s.c_id
747
                FROM $session_course_user s
748
                INNER JOIN $user u ON u.user_id = s.user_id
749
                $where $order $limit";
750
751
        $sql_query = sprintf($sql, intval($course['real_id']), $sessionId);
752
        $rs = Database::query($sql_query);
753
        while ($user = Database::fetch_array($rs)) {
754
            $users[$user['user_id']] = $user;
755
        }
756
757
        //Get survey questions
758
        $questions = SurveyManager::get_questions($surveyId, $courseId);
759
760
        //Survey is anonymous?
761
        $result = Database::query(sprintf("SELECT anonymous FROM $c_survey WHERE survey_id = %d", $surveyId));
762
        $row = Database::fetch_array($result);
763
        $anonymous = ($row['anonymous'] == 1) ? true : false;
764
765
        $table = array();
766
        foreach ($users as $user) {
767
            $data = array(
768
                'lastname' => ($anonymous ? '***' : $user[1]),
769
                'firstname' => ($anonymous ? '***' : $user[2]),
770
                'username' => ($anonymous ? '***' : $user[3]),
771
            );
772
773
            //Get questions by user
774
            $sql = "SELECT sa.question_id, sa.option_id, sqo.option_text, sq.type
775
                    FROM $c_survey_answer sa
776
                    INNER JOIN $c_survey_question sq
777
                    ON sq.question_id = sa.question_id
778
                    LEFT JOIN $c_survey_question_option sqo
779
                    ON
780
                      sqo.c_id = sa.c_id AND
781
                      sqo.question_id = sq.question_id AND
782
                      sqo.question_option_id = sa.option_id AND
783
                      sqo.survey_id = sq.survey_id
784
                    WHERE
785
                      sa.survey_id = %d AND
786
                      sa.c_id = %d AND
787
                      sa.user = %d
788
            "; //. $where_survey;
789
            $sql_query = sprintf($sql, $surveyId, $courseId, $user['user_id']);
790
791
            $result = Database::query($sql_query);
792
793
            $user_questions = array();
794
            while ($row = Database::fetch_array($result)) {
795
                $user_questions[$row['question_id']] = $row;
796
            }
797
798
            //Match course lessons with user progress
799
            foreach ($questions as $question_id => $question) {
800
                $option_text = 'option_text';
801
                if ($user_questions[$question_id]['type'] == 'open') {
802
                    $option_text = 'option_id';
803
                }
804
                $data[$question_id] = $user_questions[$question_id][$option_text];
805
            }
806
807
            $table[] = $data;
808
        }
809
        return $table;
810
    }
811
812
    /**
813
     * Gets the progress of the given session
814
     * @param int   $sessionId
815
     * @param int   $courseId
816
     * @param array options order and limit keys
817
     *
818
     * @return array table with user name, lp name, progress
819
     */
820
    public static function get_session_progress($sessionId, $courseId, $date_from, $date_to, $options)
821
    {
822
        $sessionId = intval($sessionId);
823
824
        $getAllSessions = false;
825
        if (empty($sessionId)) {
826
            $sessionId = 0;
827
            $getAllSessions = true;
828
        }
829
830
        //tables
831
        $session_course_user = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
832
        $user = Database::get_main_table(TABLE_MAIN_USER);
833
        $workTable = Database::get_course_table(TABLE_STUDENT_PUBLICATION);
834
        $workTableAssignment = Database::get_course_table(TABLE_STUDENT_PUBLICATION_ASSIGNMENT);
835
        $tbl_course_lp = Database::get_course_table(TABLE_LP_MAIN);
836
        $wiki = Database::get_course_table(TABLE_WIKI);
837
        $table_stats_default = Database::get_main_table(TABLE_STATISTIC_TRACK_E_DEFAULT);
838
        $table_stats_access = Database::get_main_table(TABLE_STATISTIC_TRACK_E_ACCESS);
839
840
        $course = api_get_course_info_by_id($courseId);
841
        $where = " WHERE c_id = '%s' AND s.status <> 2 ";
842
843
        $limit = null;
844
        if (!empty($options['limit'])) {
845
            $limit = " LIMIT " . $options['limit'];
846
        }
847
848
        if (!empty($options['where'])) {
849
            $where .= ' '.$options['where'];
850
        }
851
852
        $order = null;
853
        if (!empty($options['order'])) {
854
            $order = " ORDER BY " . $options['order'];
855
        }
856
857
        //TODO, fix create report without session
858
        $queryVariables = array($course['real_id']);
859
        if (!empty($sessionId)) {
860
            $where .= ' AND session_id = %s';
861
            $queryVariables[] = $sessionId;
862
            $sql = "SELECT
863
                        u.user_id, u.lastname, u.firstname, u.username,
864
                        u.email, s.c_id, s.session_id
865
                    FROM $session_course_user s
866
                    INNER JOIN $user u
867
                    ON u.user_id = s.user_id
868
                    $where $order $limit";
869
        } else {
870
            $sql = "SELECT
871
                        u.user_id, u.lastname, u.firstname, u.username,
872
                        u.email, s.c_id, s.session_id
873
                    FROM $session_course_user s
874
                    INNER JOIN $user u ON u.user_id = s.user_id
875
                    $where $order $limit";
876
        }
877
878
        $sql_query = vsprintf($sql, $queryVariables);
879
        $rs = Database::query($sql_query);
880
        while ($user = Database::fetch_array($rs)) {
881
            $users[$user['user_id']] = $user;
882
        }
883
884
        /**
885
         *  Lessons
886
         */
887
        $sql = "SELECT * FROM $tbl_course_lp WHERE c_id = %s ";  //AND session_id = %s
888
        $sql_query = sprintf($sql, $course['real_id']);
889
        $result = Database::query($sql_query);
890
        $arrLesson = array(array());
891 View Code Duplication
        while ($row = Database::fetch_array($result)) {
892
            if (empty($arrLesson[$row['session_id']]['lessons_total'])) {
893
                $arrLesson[$row['session_id']]['lessons_total'] = 1;
894
            } else {
895
                $arrLesson[$row['session_id']]['lessons_total'] ++;
896
            }
897
        }
898
899
        /**
900
         *  Exercises
901
         */
902
        $exercises = ExerciseLib::get_all_exercises($course, $sessionId, false, '', $getAllSessions);
903
        $exercises_total = count($exercises);
904
905
        /**
906
         *  Assignments
907
         */
908
        //total
909
        if ($getAllSessions) {
910
            $sql = "SELECT count(w.id) as count
911
                    FROM $workTable w
912
                    LEFT JOIN $workTableAssignment a
913
                    ON (a.publication_id = w.id AND a.c_id = w.c_id)
914
                    WHERE w.c_id = %s
915
                    AND parent_id = 0
916
                    AND active IN (1, 0)";
917
        } else {
918
            $sql = "SELECT count(w.id) as count
919
                    FROM $workTable w
920
                    LEFT JOIN $workTableAssignment a
921
                    ON (a.publication_id = w.id AND a.c_id = w.c_id)
922
                    WHERE w.c_id = %s
923
                    AND parent_id = 0
924
                    AND active IN (1, 0)
925
                    AND  session_id = %s";
926
        }
927
928
        $sql_query = sprintf($sql, $course['real_id'], $sessionId);
929
        $result = Database::query($sql_query);
930
        $row = Database::fetch_array($result);
931
        $assignments_total = $row['count'];
932
933
        /**
934
         * Wiki
935
         */
936
        if ($getAllSessions) {
937
            $sql = "SELECT count(distinct page_id)  as count FROM $wiki
938
                    WHERE c_id = %s";
939
        } else {
940
            $sql = "SELECT count(distinct page_id)  as count FROM $wiki
941
                    WHERE c_id = %s and session_id = %s";
942
        }
943
        $sql_query = sprintf($sql, $course['real_id'], $sessionId);
944
        $result = Database::query($sql_query);
945
        $row = Database::fetch_array($result);
946
        $wiki_total = $row['count'];
947
948
        /**
949
         * Surveys
950
         */
951
        $survey_user_list = array();
952
        $survey_list = SurveyManager::get_surveys($course['code'], $sessionId);
953
954
        $surveys_total = count($survey_list);
955 View Code Duplication
        foreach ($survey_list as $survey) {
0 ignored issues
show
Bug introduced by
The expression $survey_list of type false|array is not guaranteed to be traversable. How about adding an additional type check?

There are different options of fixing this problem.

  1. If you want to be on the safe side, you can add an additional type-check:

    $collection = json_decode($data, true);
    if ( ! is_array($collection)) {
        throw new \RuntimeException('$collection must be an array.');
    }
    
    foreach ($collection as $item) { /** ... */ }
    
  2. If you are sure that the expression is traversable, you might want to add a doc comment cast to improve IDE auto-completion and static analysis:

    /** @var array $collection */
    $collection = json_decode($data, true);
    
    foreach ($collection as $item) { /** .. */ }
    
  3. Mark the issue as a false-positive: Just hover the remove button, in the top-right corner of this issue for more options.

Loading history...
956
            $user_list = SurveyManager::get_people_who_filled_survey(
957
                $survey['survey_id'],
958
                false,
959
                $course['real_id']
960
            );
961
            foreach ($user_list as $user_id) {
962
                isset($survey_user_list[$user_id]) ? $survey_user_list[$user_id] ++ : $survey_user_list[$user_id] = 1;
963
            }
964
        }
965
966
        /**
967
         * Forums
968
         */
969
        $forums_total = CourseManager::getCountForum(
970
            $course['real_id'],
971
            $sessionId,
972
            $getAllSessions
973
        );
974
975
        //process table info
976
        foreach ($users as $user) {
977
            //Course description
978
            $sql = "SELECT count(*) as count
979
                    FROM $table_stats_access
980
                    WHERE access_tool = 'course_description'
981
                    AND c_id = '%s'
982
                    AND access_session_id = %s
983
                    AND access_user_id = %s ";
984
            $sql_query = sprintf($sql, $course['real_id'], $user['id_session'], $user['user_id']);
985
986
            $result = Database::query($sql_query);
987
            $row = Database::fetch_array($result);
988
            $course_description_progress = ($row['count'] > 0) ? 100 : 0;
989
990
            if (!empty($arrLesson[$user['id_session']]['lessons_total'])) {
991
                $lessons_total = $arrLesson[$user['id_session']]['lessons_total'];
992
            } else {
993
                $lessons_total = !empty($arrLesson[0]['lessons_total']) ? $arrLesson[0]['lessons_total'] : 0;
994
            }
995
996
            //Lessons
997
            //TODO: Lessons done and left is calculated by progress per item in lesson, maybe we should calculate it only per completed lesson?
998
            $lessons_progress = Tracking::get_avg_student_progress(
999
                $user['user_id'],
1000
                $course['code'],
1001
                array(),
1002
                $user['id_session']
1003
            );
1004
            $lessons_done = ($lessons_progress * $lessons_total) / 100;
1005
            $lessons_left = $lessons_total - $lessons_done;
1006
1007
            //Exercises
1008
            $exercises_progress = str_replace('%', '', Tracking::get_exercise_student_progress($exercises, $user['user_id'], $course['real_id'], $user['id_session']));
1009
            $exercises_done = round(($exercises_progress * $exercises_total) / 100);
1010
            $exercises_left = $exercises_total - $exercises_done;
1011
1012
            //Assignments
1013
            $assignments_done = Tracking::count_student_assignments($user['user_id'], $course['code'], $user['id_session']);
1014
            $assignments_left = $assignments_total - $assignments_done;
1015
            if (!empty($assignments_total)) {
1016
                $assignments_progress = round((( $assignments_done * 100 ) / $assignments_total), 2);
1017
            } else {
1018
                $assignments_progress = 0;
1019
            }
1020
1021
            //Wiki
1022
            //total revisions per user
1023
            $sql = "SELECT count(*) as count
1024
                    FROM $wiki
1025
                    WHERE c_id = %s and session_id = %s and user_id = %s";
1026
            $sql_query = sprintf($sql, $course['real_id'], $user['id_session'], $user['user_id']);
1027
            $result = Database::query($sql_query);
1028
            $row = Database::fetch_array($result);
1029
            $wiki_revisions = $row['count'];
1030
            //count visited wiki pages
1031
            $sql = "SELECT count(distinct default_value) as count
1032
                    FROM $table_stats_default
1033
                    WHERE
1034
                        default_user_id = %s AND
1035
                        default_event_type = 'wiki_page_view' AND
1036
                        default_value_type = 'wiki_page_id' AND
1037
                        c_id = %s
1038
                    ";
1039
            $sql_query = sprintf($sql, $user['user_id'], $course['real_id']);
1040
            $result = Database::query($sql_query);
1041
            $row = Database::fetch_array($result);
1042
1043
            $wiki_read = $row['count'];
1044
            $wiki_unread = $wiki_total - $wiki_read;
1045
            if (!empty($wiki_total)) {
1046
                $wiki_progress = round((( $wiki_read * 100 ) / $wiki_total), 2);
1047
            } else {
1048
                $wiki_progress = 0;
1049
            }
1050
1051
            //Surveys
1052
            $surveys_done = (isset($survey_user_list[$user['user_id']]) ? $survey_user_list[$user['user_id']] : 0);
1053
            $surveys_left = $surveys_total - $surveys_done;
1054
            if (!empty($surveys_total)) {
1055
                $surveys_progress = round((( $surveys_done * 100 ) / $surveys_total), 2);
1056
            } else {
1057
                $surveys_progress = 0;
1058
            }
1059
1060
            //Forums
1061
            $forums_done = CourseManager::getCountForumPerUser(
1062
                $user['user_id'],
1063
                $course['real_id'],
1064
                $user['id_session']
1065
            );
1066
            $forums_left = $forums_total - $forums_done;
1067
            if (!empty($forums_total)) {
1068
                $forums_progress = round((( $forums_done * 100 ) / $forums_total), 2);
1069
            } else {
1070
                $forums_progress = 0;
1071
            }
1072
1073
            //Overall Total
1074
            $overall_total = ($course_description_progress + $exercises_progress + $forums_progress + $assignments_progress + $wiki_progress + $surveys_progress) / 6;
1075
1076
            $link = '<a href="' . api_get_path(WEB_CODE_PATH) . 'mySpace/myStudents.php?student=' . $user[0] . '&details=true&course=' . $course['code'] . '&id_session=' . $user['id_session'] . '"> %s </a>';
1077
            $linkForum = '<a href="' . api_get_path(WEB_CODE_PATH) . 'forum/index.php?cidReq=' . $course['code'] . '&id_session=' . $user['id_session'] . '"> %s </a>';
1078
            $linkWork = '<a href="' . api_get_path(WEB_CODE_PATH) . 'work/work.php?cidReq=' . $course['code'] . '&id_session=' . $user['id_session'] . '"> %s </a>';
1079
            $linkWiki = '<a href="' . api_get_path(WEB_CODE_PATH) . 'wiki/index.php?cidReq=' . $course['code'] . '&session_id=' . $user['id_session'] . '&action=statistics"> %s </a>';
1080
            $linkSurvey = '<a href="' . api_get_path(WEB_CODE_PATH) . 'survey/survey_list.php?cidReq=' . $course['code'] . '&id_session=' . $user['id_session'] . '"> %s </a>';
1081
1082
            $table[] = array(
1083
                'lastname' => $user[1],
1084
                'firstname' => $user[2],
1085
                'username' => $user[3],
1086
                #'profile'   => '',
1087
                'total' => round($overall_total, 2) . '%',
1088
                'courses' => sprintf($link, $course_description_progress . '%'),
1089
                'lessons' => sprintf($link, $lessons_progress . '%'),
1090
                'exercises' => sprintf($link, $exercises_progress . '%'),
1091
                'forums' => sprintf($link, $forums_progress . '%'),
1092
                'homeworks' => sprintf($link, $assignments_progress . '%'),
1093
                'wikis' => sprintf($link, $wiki_progress . '%'),
1094
                'surveys' => sprintf($link, $surveys_progress . '%'),
1095
                //course description
1096
                'course_description_progress' => $course_description_progress . '%',
1097
                //lessons
1098
                'lessons_total' => sprintf($link, $lessons_total),
1099
                'lessons_done' => sprintf($link, $lessons_done),
1100
                'lessons_left' => sprintf($link, $lessons_left),
1101
                'lessons_progress' => sprintf($link, $lessons_progress . '%'),
1102
                //exercises
1103
                'exercises_total' => sprintf($link, $exercises_total),
1104
                'exercises_done' => sprintf($link, $exercises_done),
1105
                'exercises_left' => sprintf($link, $exercises_left),
1106
                'exercises_progress' => sprintf($link, $exercises_progress . '%'),
1107
                //forums
1108
                'forums_total' => sprintf($linkForum, $forums_total),
1109
                'forums_done' => sprintf($linkForum, $forums_done),
1110
                'forums_left' => sprintf($linkForum, $forums_left),
1111
                'forums_progress' => sprintf($linkForum, $forums_progress . '%'),
1112
                //assignments
1113
                'assignments_total' => sprintf($linkWork, $assignments_total),
1114
                'assignments_done' => sprintf($linkWork, $assignments_done),
1115
                'assignments_left' => sprintf($linkWork, $assignments_left),
1116
                'assignments_progress' => sprintf($linkWork, $assignments_progress . '%'),
1117
                //wiki
1118
                'wiki_total' => sprintf($linkWiki, $wiki_total),
1119
                'wiki_revisions' => sprintf($linkWiki, $wiki_revisions),
1120
                'wiki_read' => sprintf($linkWiki, $wiki_read),
1121
                'wiki_unread' => sprintf($linkWiki, $wiki_unread),
1122
                'wiki_progress' => sprintf($linkWiki, $wiki_progress . '%'),
1123
                //survey
1124
                'surveys_total' => sprintf($linkSurvey, $surveys_total),
1125
                'surveys_done' => sprintf($linkSurvey, $surveys_done),
1126
                'surveys_left' => sprintf($linkSurvey, $surveys_left),
1127
                'surveys_progress' => sprintf($linkSurvey, $surveys_progress . '%'),
1128
            );
1129
        }
1130
1131
        return $table;
1132
    }
1133
1134
    /**
1135
     * @return int
1136
     */
1137
    public static function get_number_of_tracking_access_overview()
1138
    {
1139
        // database table definition
1140
        $track_e_course_access = Database :: get_main_table(TABLE_STATISTIC_TRACK_E_COURSE_ACCESS);
1141
1142
        return Database::count_rows($track_e_course_access);
0 ignored issues
show
Deprecated Code introduced by
The method Database::count_rows() has been deprecated.

This method has been deprecated.

Loading history...
1143
    }
1144
1145
    /**
1146
     * Get the ip, total of clicks, login date and time logged in for all user, in one session
1147
     * @todo track_e_course_access table should have ip so we dont have to look for it in track_e_login
1148
     *
1149
     * @author César Perales <[email protected]>, Beeznest Team
1150
     * @version 1.9.6
1151
     */
1152
    public static function get_user_data_access_tracking_overview(
1153
        $sessionId,
1154
        $courseId,
1155
        $studentId = 0,
1156
        $profile = '',
1157
        $date_from = '',
1158
        $date_to = '',
1159
        $options
1160
    ) {
1161
        //escaping variables
1162
        $sessionId = intval($sessionId);
1163
        $courseId = intval($courseId);
1164
        $studentId = intval($studentId);
1165
        $profile = intval($profile);
1166
        $date_from = Database::escape_string($date_from);
1167
        $date_to = Database::escape_string($date_to);
1168
1169
        // database table definition
1170
        $user = Database :: get_main_table(TABLE_MAIN_USER);
1171
        $course = Database :: get_main_table(TABLE_MAIN_COURSE);
1172
        $track_e_login = Database :: get_main_table(TABLE_STATISTIC_TRACK_E_LOGIN);
1173
        $track_e_course_access = Database :: get_main_table(TABLE_STATISTIC_TRACK_E_COURSE_ACCESS);
1174
        $sessionTable = Database :: get_main_table(TABLE_MAIN_SESSION);
1175
1176
        global $export_csv;
1177
        if ($export_csv) {
1178
            $is_western_name_order = api_is_western_name_order(PERSON_NAME_DATA_EXPORT);
1179
        } else {
1180
            $is_western_name_order = api_is_western_name_order();
1181
        }
1182
1183
        $where = null;
1184
        if (isset($sessionId) && !empty($sessionId)) {
1185
            $where = sprintf(" WHERE a.session_id = %d", $sessionId);
1186
        }
1187
        if (isset($courseId) && !empty($courseId)) {
1188
            $where .= sprintf(" AND c.id = %d", $courseId);
1189
        }
1190
        if (isset($studentId) && !empty($studentId)) {
1191
            $where .= sprintf(" AND u.user_id = %d", $studentId);
1192
        }
1193
        if (isset($profile) && !empty($profile)) {
1194
            $where .= sprintf(" AND u.status = %d", $profile);
1195
        }
1196
        if (!empty($date_to) && !empty($date_from)) {
1197
            $where .= sprintf(
1198
                " AND a.login_course_date >= '%s 00:00:00'
1199
                 AND a.login_course_date <= '%s 23:59:59'",
1200
                $date_from,
1201
                $date_to
1202
            );
1203
        }
1204
1205
        $limit = null;
1206
        if (!empty($options['limit'])) {
1207
            $limit = " LIMIT " . $options['limit'];
1208
        }
1209
1210
        if (!empty($options['where'])) {
1211
            $where .= ' '.$options['where'];
1212
        }
1213
1214
        $order = null;
1215
        if (!empty($options['order'])) {
1216
            $order = " ORDER BY " . $options['order'];
1217
        }
1218
1219
        //TODO add course name
1220
        $sql = "SELECT
1221
                a.login_course_date ,
1222
                u.username ,
1223
                " . ($is_western_name_order ? "
1224
                    u.firstname,
1225
                    u.lastname,
1226
                    " : "
1227
                    u.lastname,
1228
                    u.firstname,
1229
                ") . "
1230
                a.logout_course_date,
1231
                a.counter,
1232
                c.title,
1233
                c.code,
1234
                u.user_id,
1235
                a.session_id
1236
            FROM $track_e_course_access a
1237
            INNER JOIN $user u ON a.user_id = u.user_id
1238
            INNER JOIN $course c ON a.c_id = c.id
1239
            $where $order $limit";
1240
        $result = Database::query(sprintf($sql, $sessionId, $courseId));
1241
1242
        $data = array();
1243
        while ($user = Database::fetch_assoc($result)) {
1244
            $data[] = $user;
1245
        }
1246
1247
        //foreach
1248
        foreach ($data as $key => $info) {
1249
1250
            $sql = "SELECT
1251
                    name
1252
                    FROM $sessionTable
1253
                    WHERE
1254
                    id = {$info['session_id']}";
1255
            $result = Database::query($sql);
1256
            $session = Database::fetch_assoc($result);
1257
1258
            // building array to display
1259
            $return[] = array(
1260
                'user_id' => $info['user_id'],
1261
                'logindate' => $info['login_course_date'],
1262
                'username' => $info['username'],
1263
                'firstname' => $info['firstname'],
1264
                'lastname' => $info['lastname'],
1265
                'clicks' => $info['counter'], //+ $clicks[$info['user_id']],
1266
                'ip' => '',
1267
                'timeLoggedIn' => gmdate("H:i:s", strtotime($info['logout_course_date']) - strtotime($info['login_course_date'])),
1268
                'session' => $session['name']
1269
            );
1270
        }
1271
1272
        foreach ($return as $key => $info) {
1273
            //Search for ip, we do less querys if we iterate the final array
1274
            $sql = sprintf("SELECT user_ip FROM $track_e_login WHERE login_user_id = %d AND login_date < '%s' ORDER BY login_date DESC LIMIT 1", $info['user_id'], $info['logindate']); //TODO add select by user too
1275
            $result = Database::query($sql);
1276
            $ip = Database::fetch_assoc($result);
1277
            //if no ip founded, we search the closest higher ip
1278
            if (empty($ip['user_ip'])) {
1279
                $sql = sprintf("SELECT user_ip FROM $track_e_login WHERE login_user_id = %d AND login_date > '%s'  ORDER BY login_date ASC LIMIT 1", $info['user_id'], $info['logindate']); //TODO add select by user too
1280
                $result = Database::query($sql);
1281
                $ip = Database::fetch_assoc($result);
1282
            }
1283
            #add ip to final array
1284
            $return[$key]['ip'] = $ip['user_ip'];
1285
        }
1286
        return $return;
1287
    }
1288
1289
    /**
1290
     * Creates a new course code based in given code
1291
     *
1292
     * @param string	$session_name
1293
     * <code>
1294
     * $wanted_code = 'curse' if there are in the DB codes like curse1 curse2 the function will return: course3
1295
     * if the course code doest not exist in the DB the same course code will be returned
1296
     * </code>
1297
     * @return string	wanted unused code
1298
     */
1299 View Code Duplication
    public static function generateNextSessionName($session_name)
1300
    {
1301
        $session_name_ok = !self::session_name_exists($session_name);
1302
        if (!$session_name_ok) {
1303
            $table = Database::get_main_table(TABLE_MAIN_SESSION);
1304
            $session_name = Database::escape_string($session_name);
1305
            $sql = "SELECT count(*) as count FROM $table
1306
                    WHERE name LIKE '$session_name%'";
1307
            $result = Database::query($sql);
1308
            if (Database::num_rows($result) > 0) {
1309
                $row = Database::fetch_array($result);
1310
                $count = $row['count'] + 1;
1311
                $session_name = $session_name . '_' . $count;
1312
                $result = self::session_name_exists($session_name);
1313
                if (!$result) {
1314
                    return $session_name;
1315
                }
1316
            }
1317
            return false;
1318
        }
1319
        return $session_name;
1320
    }
1321
1322
    /**
1323
     * Edit a session
1324
     * @author Carlos Vargas from existing code
1325
     * @param integer   $id Session primary key
1326
     * @param string    $name
1327
     * @param string    $startDate
1328
     * @param string    $endDate
1329
     * @param string    $displayStartDate
1330
     * @param string    $displayEndDate
1331
     * @param string    $coachStartDate
1332
     * @param string    $coachEndDate
1333
     * @param integer   $coachId
1334
     * @param integer   $sessionCategoryId
1335
     * @param int       $visibility
1336
     * @param string    $description
1337
     * @param bool      $showDescription
1338
     * @param int       $duration
1339
     * @param array     $extraFields
1340
     * @param int       $sessionAdminId
1341
     * @param boolean $sendSubscriptionNotification Optional.
1342
     *          Whether send a mail notification to users being subscribed
1343
     * @return mixed
1344
     */
1345
    public static function edit_session(
1346
        $id,
1347
        $name,
1348
        $startDate,
1349
        $endDate,
1350
        $displayStartDate,
1351
        $displayEndDate,
1352
        $coachStartDate,
1353
        $coachEndDate,
1354
        $coachId,
1355
        $sessionCategoryId,
1356
        $visibility,
1357
        $description = null,
1358
        $showDescription = 0,
1359
        $duration = null,
1360
        $extraFields = array(),
1361
        $sessionAdminId = 0,
1362
        $sendSubscriptionNotification = false
1363
    ) {
1364
        $name = trim(stripslashes($name));
1365
        $coachId = intval($coachId);
1366
        $sessionCategoryId = intval($sessionCategoryId);
1367
        $visibility = intval($visibility);
1368
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
1369
1370
        if (empty($name)) {
1371
            Display::return_message(get_lang('SessionNameIsRequired'), 'warning');
1372
1373
            return false;
1374
        } elseif (empty($coachId)) {
1375
            Display::return_message(get_lang('CoachIsRequired'), 'warning');
1376
1377
            return false;
1378
        } elseif (!empty($startDate) && !api_is_valid_date($startDate, 'Y-m-d H:i')) {
1379
            Display::return_message(get_lang('InvalidStartDate'), 'warning');
1380
1381
            return false;
1382
        } elseif (!empty($endDate) && !api_is_valid_date($endDate, 'Y-m-d H:i')) {
1383
            Display::return_message(get_lang('InvalidEndDate'), 'warning');
1384
1385
            return false;
1386
        } elseif (!empty($startDate) && !empty($endDate) && $startDate >= $endDate) {
1387
            Display::return_message(get_lang('StartDateShouldBeBeforeEndDate'), 'warning');
1388
1389
            return false;
1390
        } else {
1391
            $sql = "SELECT id FROM $tbl_session WHERE name='" . Database::escape_string($name) . "'";
1392
            $rs = Database::query($sql);
1393
            $exists = false;
1394
            while ($row = Database::fetch_array($rs)) {
1395
                if ($row['id'] != $id) {
1396
                    $exists = true;
1397
                }
1398
            }
1399
1400
            if ($exists) {
1401
                Display::return_message(get_lang('SessionNameAlreadyExists'), 'warning');
1402
1403
                return false;
1404
            } else {
1405
                $values = [
1406
                    'name' => $name,
1407
                    'duration' => $duration,
1408
                    'id_coach' => $coachId,
1409
                    'description'=> $description,
1410
                    'show_description' => intval($showDescription),
1411
                    'visibility' => $visibility,
1412
                    'send_subscription_notification' => $sendSubscriptionNotification
1413
                ];
1414
1415
                if (!empty($sessionAdminId)) {
1416
                    $values['session_admin_id'] = $sessionAdminId;
1417
                }
1418
1419
                if (!empty($startDate)) {
1420
                    $values['access_start_date'] = api_get_utc_datetime($startDate);
1421
                }
1422
1423
                if (!empty($endDate)) {
1424
                    $values['access_end_date'] = api_get_utc_datetime($endDate);
1425
                }
1426
1427
                if (!empty($displayStartDate)) {
1428
                    $values['display_start_date'] = api_get_utc_datetime($displayStartDate);
1429
                }
1430
1431
                if (!empty($displayEndDate)) {
1432
                    $values['display_end_date'] = api_get_utc_datetime($displayEndDate);
1433
                }
1434
1435
                if (!empty($coachStartDate)) {
1436
                    $values['coach_access_start_date'] = api_get_utc_datetime($coachStartDate);
1437
                }
1438
                if (!empty($coachEndDate)) {
1439
                    $values['coach_access_end_date'] = api_get_utc_datetime($coachEndDate);
1440
                }
1441
1442
                if (!empty($sessionCategoryId)) {
1443
                    $values['session_category_id'] = $sessionCategoryId;
1444
                }
1445
1446
                Database::update($tbl_session, $values, array(
1447
                    'id = ?' => $id
1448
                ));
1449
1450
                if (!empty($extraFields)) {
1451
                    $extraFields['item_id'] = $id;
1452
                    $sessionFieldValue = new ExtraFieldValue('session');
1453
                    $sessionFieldValue->saveFieldValues($extraFields);
1454
                }
1455
1456
                return $id;
1457
            }
1458
        }
1459
    }
1460
1461
    /**
1462
     * Delete session
1463
     * @author Carlos Vargas  from existing code
1464
     * @param	array	$id_checked an array to delete sessions
1465
     * @param   boolean  $from_ws optional, true if the function is called
1466
     * by a webservice, false otherwise.
1467
     * @return	void	Nothing, or false on error
1468
     * */
1469
    public static function delete($id_checked, $from_ws = false)
1470
    {
1471
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
1472
        $tbl_session_rel_course = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
1473
        $tbl_session_rel_course_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
1474
        $tbl_session_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_USER);
1475
        $tbl_url_session = Database::get_main_table(TABLE_MAIN_ACCESS_URL_REL_SESSION);
1476
        $tbl_item_properties = Database::get_course_table(TABLE_ITEM_PROPERTY);
1477
        $em = Database::getManager();
1478
1479
        $userId = api_get_user_id();
1480
1481
        if (is_array($id_checked)) {
1482
            foreach ($id_checked as $sessionId) {
1483
                self::delete($sessionId);
1484
            }
1485
        } else {
1486
            $id_checked = intval($id_checked);
1487
        }
1488
1489
        if (SessionManager::allowed($id_checked) && !$from_ws) {
0 ignored issues
show
Bug introduced by
It seems like $id_checked defined by parameter $id_checked on line 1469 can also be of type array; however, SessionManager::allowed() does only seem to accept integer, maybe add an additional type check?

This check looks at variables that have been passed in as parameters and are passed out again to other methods.

If the outgoing method call has stricter type requirements than the method itself, an issue is raised.

An additional type check may prevent trouble.

Loading history...
1490
            $qb = $em
1491
                ->createQuery('
1492
                    SELECT s.sessionAdminId FROM ChamiloCoreBundle:Session s
1493
                    WHERE s.id = ?1
1494
                ')
1495
                ->setParameter(1, $id_checked);
1496
1497
            $res = $qb->getSingleScalarResult();
1498
1499
            if ($res != $userId) {
1500
                api_not_allowed(true);
1501
            }
1502
        }
1503
1504
        // Delete documents inside a session
1505
        $courses = SessionManager::getCoursesInSession($id_checked);
1506
        foreach ($courses as $courseId) {
1507
            $courseInfo = api_get_course_info_by_id($courseId);
1508
            DocumentManager::deleteDocumentsFromSession($courseInfo, $id_checked);
0 ignored issues
show
Bug introduced by
It seems like $id_checked defined by parameter $id_checked on line 1469 can also be of type array; however, DocumentManager::deleteDocumentsFromSession() does only seem to accept integer, maybe add an additional type check?

This check looks at variables that have been passed in as parameters and are passed out again to other methods.

If the outgoing method call has stricter type requirements than the method itself, an issue is raised.

An additional type check may prevent trouble.

Loading history...
1509
        }
1510
1511
        Database::query("DELETE FROM $tbl_session_rel_course WHERE session_id IN($id_checked)");
1512
        Database::query("DELETE FROM $tbl_session_rel_course_rel_user WHERE session_id IN($id_checked)");
1513
        Database::query("DELETE FROM $tbl_session_rel_user WHERE session_id IN($id_checked)");
1514
        Database::query("DELETE FROM $tbl_item_properties WHERE session_id IN ($id_checked)");
1515
        Database::query("DELETE FROM $tbl_url_session WHERE session_id IN($id_checked)");
1516
1517
        Database::query("DELETE FROM $tbl_session WHERE id IN ($id_checked)");
1518
1519
        $extraFieldValue = new ExtraFieldValue('session');
1520
        $extraFieldValue->deleteValuesByItem($id_checked);
0 ignored issues
show
Bug introduced by
It seems like $id_checked defined by parameter $id_checked on line 1469 can also be of type array; however, ExtraFieldValue::deleteValuesByItem() does only seem to accept integer, maybe add an additional type check?

This check looks at variables that have been passed in as parameters and are passed out again to other methods.

If the outgoing method call has stricter type requirements than the method itself, an issue is raised.

An additional type check may prevent trouble.

Loading history...
1521
1522
        /** @var \Chamilo\CoreBundle\Entity\Repository\SequenceRepository $repo */
1523
        $repo = Database::getManager()->getRepository('ChamiloCoreBundle:SequenceResource');
1524
        $repo->deleteResource(
1525
            $id_checked,
0 ignored issues
show
Bug introduced by
It seems like $id_checked defined by parameter $id_checked on line 1469 can also be of type array; however, Chamilo\CoreBundle\Entit...itory::deleteResource() does only seem to accept integer, maybe add an additional type check?

This check looks at variables that have been passed in as parameters and are passed out again to other methods.

If the outgoing method call has stricter type requirements than the method itself, an issue is raised.

An additional type check may prevent trouble.

Loading history...
1526
            \Chamilo\CoreBundle\Entity\SequenceResource::SESSION_TYPE
1527
        );
1528
1529
        // Add event to system log
1530
        Event::addEvent(
1531
            LOG_SESSION_DELETE,
1532
            LOG_SESSION_ID,
1533
            $id_checked,
1534
            api_get_utc_datetime(),
1535
            $userId
1536
        );
1537
    }
1538
1539
    /**
1540
     * @param int $id_promotion
1541
     *
1542
     * @return bool
1543
     */
1544 View Code Duplication
    public static function clear_session_ref_promotion($id_promotion)
1545
    {
1546
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
1547
        $id_promotion = intval($id_promotion);
1548
        $sql = "UPDATE $tbl_session SET promotion_id=0
1549
                WHERE promotion_id = $id_promotion";
1550
        if (Database::query($sql)) {
1551
            return true;
1552
        } else {
1553
            return false;
1554
        }
1555
    }
1556
1557
    /**
1558
     * Subscribes students to the given session and optionally (default) unsubscribes previous users
1559
     *
1560
     * @author Carlos Vargas from existing code
1561
     * @author Julio Montoya. Cleaning code.
1562
     * @param int $id_session
1563
     * @param array $user_list
1564
     * @param int $session_visibility
1565
     * @param bool $empty_users
1566
     * @return bool
1567
     */
1568
    public static function suscribe_users_to_session(
1569
        $id_session,
1570
        $user_list,
1571
        $session_visibility = SESSION_VISIBLE_READ_ONLY,
1572
        $empty_users = true
1573
    ) {
1574
        if ($id_session != strval(intval($id_session))) {
1575
            return false;
1576
        }
1577
1578
        foreach ($user_list as $intUser) {
1579
            if ($intUser != strval(intval($intUser))) {
1580
                return false;
1581
            }
1582
        }
1583
1584
        $tbl_session_rel_course = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
1585
        $tbl_session_rel_course_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
1586
        $tbl_session_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_USER);
1587
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
1588
1589
        $entityManager = Database::getManager();
1590
        $session = $entityManager->find('ChamiloCoreBundle:Session', $id_session);
1591
1592
        // from function parameter
1593
        if (empty($session_visibility)) {
1594
            $session_visibility = $session->getVisibility();
1595
            //default status loaded if empty
1596
            if (empty($session_visibility))
1597
                $session_visibility = SESSION_VISIBLE_READ_ONLY; // by default readonly 1
1598
        } else {
1599
            if (!in_array($session_visibility, array(SESSION_VISIBLE_READ_ONLY, SESSION_VISIBLE, SESSION_INVISIBLE))) {
1600
                $session_visibility = SESSION_VISIBLE_READ_ONLY;
1601
            }
1602
        }
1603
1604
        $sql = "SELECT user_id FROM $tbl_session_rel_course_rel_user
1605
                WHERE session_id = $id_session AND status = 0";
1606
        $result = Database::query($sql);
1607
        $existingUsers = array();
1608
        while ($row = Database::fetch_array($result)) {
1609
            $existingUsers[] = $row['user_id'];
1610
        }
1611
1612
        $sql = "SELECT c_id FROM $tbl_session_rel_course
1613
                WHERE session_id = $id_session";
1614
        $result = Database::query($sql);
1615
        $course_list = array();
1616
        while ($row = Database::fetch_array($result)) {
1617
            $course_list[] = $row['c_id'];
1618
        }
1619
1620
        if (
1621
            $session->getSendSubscriptionNotification() &&
1622
            is_array($user_list)
1623
        ) {
1624
            // Sending emails only
1625
            foreach ($user_list as $user_id) {
1626
                if (in_array($user_id, $existingUsers)) {
1627
                    continue;
1628
                }
1629
1630
                $tplSubject = new Template(null, false, false, false, false, false);
1631
                $layoutSubject = $tplSubject->get_template(
1632
                    'mail/subject_subscription_to_session_confirmation.tpl'
1633
                );
1634
                $subject = $tplSubject->fetch($layoutSubject);
1635
1636
                $user_info = api_get_user_info($user_id);
1637
1638
                $tplContent = new Template(null, false, false, false, false, false);
1639
                // Variables for default template
1640
                $tplContent->assign(
1641
                    'complete_name',
1642
                    stripslashes($user_info['complete_name'])
1643
                );
1644
                $tplContent->assign('session_name', $session->getName());
1645
                $tplContent->assign(
1646
                    'session_coach',
1647
                    $session->getGeneralCoach()->getCompleteName()
1648
                );
1649
                $layoutContent = $tplContent->get_template(
1650
                    'mail/content_subscription_to_session_confirmation.tpl'
1651
                );
1652
                $content = $tplContent->fetch($layoutContent);
1653
1654
                api_mail_html(
1655
                    $user_info['complete_name'],
1656
                    $user_info['mail'],
1657
                    $subject,
1658
                    $content,
1659
                    api_get_person_name(
1660
                        api_get_setting('administratorName'),
1661
                        api_get_setting('administratorSurname')
1662
                    ),
1663
                    api_get_setting('emailAdministrator')
1664
                );
1665
            }
1666
        }
1667
1668
        foreach ($course_list as $courseId) {
1669
            // for each course in the session
1670
            $nbr_users = 0;
1671
            $courseId = intval($courseId);
1672
1673
            $sql = "SELECT DISTINCT user_id
1674
                    FROM $tbl_session_rel_course_rel_user
1675
                    WHERE
1676
                        session_id = $id_session AND
1677
                        c_id = $courseId AND
1678
                        status = 0
1679
                    ";
1680
            $result = Database::query($sql);
1681
            $existingUsers = array();
1682
            while ($row = Database::fetch_array($result)) {
1683
                $existingUsers[] = $row['user_id'];
1684
            }
1685
1686
            // Delete existing users
1687 View Code Duplication
            if ($empty_users) {
1688
                foreach ($existingUsers as $existing_user) {
1689
                    if (!in_array($existing_user, $user_list)) {
1690
                        $sql = "DELETE FROM $tbl_session_rel_course_rel_user
1691
                                WHERE
1692
                                    session_id = $id_session AND
1693
                                    c_id = $courseId AND
1694
                                    user_id = $existing_user AND
1695
                                    status = 0 ";
1696
                        $result = Database::query($sql);
1697
1698
                        Event::addEvent(
1699
                            LOG_SESSION_DELETE_USER_COURSE,
1700
                            LOG_USER_ID,
1701
                            $existing_user,
1702
                            api_get_utc_datetime(),
1703
                            api_get_user_id(),
1704
                            $courseId,
1705
                            $id_session
1706
                        );
1707
1708
                        if (Database::affected_rows($result)) {
1709
                            $nbr_users--;
1710
                        }
1711
                    }
1712
                }
1713
            }
1714
1715
            // Replace with this new function
1716
            // insert new users into session_rel_course_rel_user and ignore if they already exist
1717
1718
            foreach ($user_list as $enreg_user) {
1719 View Code Duplication
                if (!in_array($enreg_user, $existingUsers)) {
1720
                    $enreg_user = Database::escape_string($enreg_user);
1721
                    $sql = "INSERT IGNORE INTO $tbl_session_rel_course_rel_user (session_id, c_id, user_id, visibility, status)
1722
                            VALUES($id_session, $courseId, $enreg_user, $session_visibility, 0)";
1723
                    $result = Database::query($sql);
1724
1725
                    Event::addEvent(
1726
                        LOG_SESSION_ADD_USER_COURSE,
1727
                        LOG_USER_ID,
1728
                        $enreg_user,
1729
                        api_get_utc_datetime(),
1730
                        api_get_user_id(),
1731
                        $courseId,
1732
                        $id_session
1733
                    );
1734
1735
                    if (Database::affected_rows($result)) {
1736
1737
                        $nbr_users++;
1738
                    }
1739
                }
1740
            }
1741
1742
            // Count users in this session-course relation
1743
            $sql = "SELECT COUNT(user_id) as nbUsers
1744
                    FROM $tbl_session_rel_course_rel_user
1745
                    WHERE session_id = $id_session AND c_id = $courseId AND status<>2";
1746
            $rs = Database::query($sql);
1747
            list($nbr_users) = Database::fetch_array($rs);
0 ignored issues
show
Bug introduced by
It seems like $rs can be null; however, fetch_array() does not accept null, maybe add an additional type check?

Unless you are absolutely sure that the expression can never be null because of other conditions, we strongly recommend to add an additional type check to your code:

/** @return stdClass|null */
function mayReturnNull() { }

function doesNotAcceptNull(stdClass $x) { }

// With potential error.
function withoutCheck() {
    $x = mayReturnNull();
    doesNotAcceptNull($x); // Potential error here.
}

// Safe - Alternative 1
function withCheck1() {
    $x = mayReturnNull();
    if ( ! $x instanceof stdClass) {
        throw new \LogicException('$x must be defined.');
    }
    doesNotAcceptNull($x);
}

// Safe - Alternative 2
function withCheck2() {
    $x = mayReturnNull();
    if ($x instanceof stdClass) {
        doesNotAcceptNull($x);
    }
}
Loading history...
1748
            // update the session-course relation to add the users total
1749
            $sql = "UPDATE $tbl_session_rel_course SET nbr_users = $nbr_users
1750
                    WHERE session_id = $id_session AND c_id = $courseId";
1751
            Database::query($sql);
1752
        }
1753
1754
        // Delete users from the session
1755
        if ($empty_users === true) {
1756
            $sql = "DELETE FROM $tbl_session_rel_user
1757
                    WHERE session_id = $id_session AND relation_type<>" . SESSION_RELATION_TYPE_RRHH . "";
1758
            Database::query($sql);
1759
        }
1760
1761
        // Insert missing users into session
1762
        $nbr_users = 0;
1763
1764
        foreach ($user_list as $enreg_user) {
1765
            $enreg_user = Database::escape_string($enreg_user);
1766
            $nbr_users++;
1767
            $sql = "INSERT IGNORE INTO $tbl_session_rel_user (relation_type, session_id, user_id, registered_at)
1768
                    VALUES (0, $id_session, $enreg_user, '" . api_get_utc_datetime() . "')";
1769
            Database::query($sql);
1770
        }
1771
1772
        // update number of users in the session
1773
        $nbr_users = count($user_list);
1774
        if ($empty_users) {
1775
            // update number of users in the session
1776
            $sql = "UPDATE $tbl_session SET nbr_users= $nbr_users
1777
                    WHERE id = $id_session ";
1778
            Database::query($sql);
1779
        } else {
1780
            $sql = "UPDATE $tbl_session SET nbr_users = nbr_users + $nbr_users
1781
                    WHERE id = $id_session";
1782
            Database::query($sql);
1783
        }
1784
    }
1785
1786
    /**
1787
     * Returns user list of the current users subscribed in the course-session
1788
     * @param int $sessionId
1789
     * @param array $courseInfo
1790
     * @param int $status
1791
     *
1792
     * @return array
1793
     */
1794
    public static function getUsersByCourseSession(
1795
        $sessionId,
1796
        $courseInfo,
1797
        $status = null
1798
    ) {
1799
        $sessionId = intval($sessionId);
1800
        $courseCode = $courseInfo['code'];
1801
        $courseId = $courseInfo['real_id'];
1802
1803
        if (empty($sessionId) || empty($courseCode)) {
1804
            return array();
1805
        }
1806
1807
        $statusCondition = null;
1808 View Code Duplication
        if (isset($status) && !is_null($status)) {
1809
            $status = intval($status);
1810
            $statusCondition = " AND status = $status";
1811
        }
1812
1813
        $table = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
1814
1815
        $sql = "SELECT DISTINCT user_id
1816
                FROM $table
1817
                WHERE
1818
                    session_id = $sessionId AND
1819
                    c_id = $courseId
1820
                    $statusCondition
1821
                ";
1822
        $result = Database::query($sql);
1823
        $existingUsers = array();
1824
        while ($row = Database::fetch_array($result)) {
1825
            $existingUsers[] = $row['user_id'];
1826
        }
1827
1828
        return $existingUsers;
1829
    }
1830
1831
    /**
1832
     * Remove a list of users from a course-session
1833
     * @param array $userList
1834
     * @param int $sessionId
1835
     * @param array $courseInfo
1836
     * @param int $status
1837
     * @param bool $updateTotal
1838
     * @return bool
1839
     */
1840
    public static function removeUsersFromCourseSession(
1841
        $userList,
1842
        $sessionId,
1843
        $courseInfo,
1844
        $status = null,
1845
        $updateTotal = true
1846
    ) {
1847
        $table = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
1848
        $tableSessionCourse = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
1849
        $sessionId = intval($sessionId);
1850
1851
        if (empty($sessionId) || empty($userList) || empty($courseInfo)) {
1852
            return false;
1853
        }
1854
1855
        is_array($courseInfo) ? $courseId = $courseInfo['real_id'] : $courseId = $courseInfo;
1856
1857
        $statusCondition = null;
1858 View Code Duplication
        if (isset($status) && !is_null($status))  {
1859
            $status = intval($status);
1860
            $statusCondition  = " AND status = $status";
1861
        }
1862
1863
        foreach ($userList as $userId) {
1864
            $userId = intval($userId);
1865
            $sql = "DELETE FROM $table
1866
                    WHERE
1867
                        session_id = $sessionId AND
1868
                        c_id = $courseId AND
1869
                        user_id = $userId
1870
                        $statusCondition
1871
                    ";
1872
            Database::query($sql);
1873
        }
1874
1875
        if ($updateTotal) {
1876
            // Count users in this session-course relation
1877
            $sql = "SELECT COUNT(user_id) as nbUsers
1878
                    FROM $table
1879
                    WHERE
1880
                        session_id = $sessionId AND
1881
                        c_id = $courseId AND
1882
                        status <> 2";
1883
            $result = Database::query($sql);
1884
            list($userCount) = Database::fetch_array($result);
0 ignored issues
show
Bug introduced by
It seems like $result can be null; however, fetch_array() does not accept null, maybe add an additional type check?

Unless you are absolutely sure that the expression can never be null because of other conditions, we strongly recommend to add an additional type check to your code:

/** @return stdClass|null */
function mayReturnNull() { }

function doesNotAcceptNull(stdClass $x) { }

// With potential error.
function withoutCheck() {
    $x = mayReturnNull();
    doesNotAcceptNull($x); // Potential error here.
}

// Safe - Alternative 1
function withCheck1() {
    $x = mayReturnNull();
    if ( ! $x instanceof stdClass) {
        throw new \LogicException('$x must be defined.');
    }
    doesNotAcceptNull($x);
}

// Safe - Alternative 2
function withCheck2() {
    $x = mayReturnNull();
    if ($x instanceof stdClass) {
        doesNotAcceptNull($x);
    }
}
Loading history...
1885
1886
            // update the session-course relation to add the users total
1887
            $sql = "UPDATE $tableSessionCourse
1888
                    SET nbr_users = $userCount
1889
                    WHERE
1890
                        session_id = $sessionId AND
1891
                        c_id = $courseId";
1892
            Database::query($sql);
1893
        }
1894
    }
1895
1896
    /**
1897
     * Subscribe a user to an specific course inside a session.
1898
     *
1899
     * @param array $user_list
1900
     * @param int $session_id
1901
     * @param string $course_code
1902
     * @param int $session_visibility
1903
     * @param bool $removeUsersNotInList
1904
     * @return bool
1905
     */
1906
    public static function subscribe_users_to_session_course(
1907
        $user_list,
1908
        $session_id,
1909
        $course_code,
1910
        $session_visibility = SESSION_VISIBLE_READ_ONLY,
1911
        $removeUsersNotInList = false
1912
    ) {
1913
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
1914
        $tbl_session_rel_course = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
1915
        $tbl_session_rel_course_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
1916
        $tbl_session_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_USER);
1917
1918
        if (empty($session_id) || empty($course_code)) {
1919
            return false;
1920
        }
1921
1922
        $session_id = intval($session_id);
1923
        $course_code = Database::escape_string($course_code);
1924
        $courseInfo = api_get_course_info($course_code);
1925
        $courseId = $courseInfo['real_id'];
1926
1927
        $session_visibility = intval($session_visibility);
1928
1929
        if ($removeUsersNotInList) {
1930
1931
            $currentUsers = self::getUsersByCourseSession($session_id, $courseInfo, 0);
1932
1933
            if (!empty($user_list)) {
1934
                $userToDelete = array_diff($currentUsers, $user_list);
1935
            } else {
1936
                $userToDelete = $currentUsers;
1937
            }
1938
1939
            if (!empty($userToDelete)) {
1940
                self::removeUsersFromCourseSession(
1941
                    $userToDelete,
1942
                    $session_id,
1943
                    $courseInfo,
1944
                    0,
1945
                    true
1946
                );
1947
            }
1948
        }
1949
1950
        $nbr_users = 0;
1951
        foreach ($user_list as $enreg_user) {
1952
            $enreg_user = intval($enreg_user);
1953
            // Checking if user exists in session - course - user table.
1954
            $sql = "SELECT count(user_id) as count
1955
                    FROM $tbl_session_rel_course_rel_user
1956
                    WHERE
1957
                        session_id = $session_id AND
1958
                        c_id = $courseId and
1959
                        user_id = $enreg_user ";
1960
            $result = Database::query($sql);
1961
            $count = 0;
1962
1963
            if (Database::num_rows($result) > 0) {
1964
                $row = Database::fetch_array($result, 'ASSOC');
1965
                $count = $row['count'];
1966
            }
1967
1968
            if ($count == 0) {
1969
                $sql = "INSERT IGNORE INTO $tbl_session_rel_course_rel_user (session_id, c_id, user_id, visibility)
1970
                        VALUES ($session_id, $courseId, $enreg_user, $session_visibility)";
1971
                $result = Database::query($sql);
1972
                if (Database::affected_rows($result)) {
1973
                    $nbr_users++;
1974
                }
1975
            }
1976
1977
            // Checking if user exists in session - user table.
1978
            $sql = "SELECT count(user_id) as count
1979
                    FROM $tbl_session_rel_user
1980
                    WHERE session_id = $session_id AND user_id = $enreg_user ";
1981
            $result = Database::query($sql);
1982
            $count = 0;
1983
1984
            if (Database::num_rows($result) > 0) {
1985
                $row = Database::fetch_array($result, 'ASSOC');
1986
                $count = $row['count'];
1987
            }
1988
1989 View Code Duplication
            if (empty($count)) {
1990
                // If user is not registered to a session then add it.
1991
                $sql = "INSERT IGNORE INTO $tbl_session_rel_user (session_id, user_id, registered_at)
1992
                        VALUES ($session_id, $enreg_user, '" . api_get_utc_datetime() . "')";
1993
                Database::query($sql);
1994
1995
                $sql = "UPDATE $tbl_session SET nbr_users = nbr_users + 1
1996
                        WHERE id = $session_id ";
1997
                Database::query($sql);
1998
            }
1999
        }
2000
2001
        // count users in this session-course relation
2002
        $sql = "SELECT COUNT(user_id) as nbUsers
2003
                FROM $tbl_session_rel_course_rel_user
2004
                WHERE session_id = $session_id AND c_id = $courseId AND status <> 2";
2005
        $rs = Database::query($sql);
2006
        list($nbr_users) = Database::fetch_array($rs);
0 ignored issues
show
Bug introduced by
It seems like $rs can be null; however, fetch_array() does not accept null, maybe add an additional type check?

Unless you are absolutely sure that the expression can never be null because of other conditions, we strongly recommend to add an additional type check to your code:

/** @return stdClass|null */
function mayReturnNull() { }

function doesNotAcceptNull(stdClass $x) { }

// With potential error.
function withoutCheck() {
    $x = mayReturnNull();
    doesNotAcceptNull($x); // Potential error here.
}

// Safe - Alternative 1
function withCheck1() {
    $x = mayReturnNull();
    if ( ! $x instanceof stdClass) {
        throw new \LogicException('$x must be defined.');
    }
    doesNotAcceptNull($x);
}

// Safe - Alternative 2
function withCheck2() {
    $x = mayReturnNull();
    if ($x instanceof stdClass) {
        doesNotAcceptNull($x);
    }
}
Loading history...
2007
        // update the session-course relation to add the users total
2008
        $sql = "UPDATE $tbl_session_rel_course
2009
                SET nbr_users = $nbr_users
2010
                WHERE session_id = $session_id AND c_id = $courseId";
2011
        Database::query($sql);
2012
    }
2013
2014
    /**
2015
     * Unsubscribe user from session
2016
     *
2017
     * @param int Session id
2018
     * @param int User id
2019
     * @return bool True in case of success, false in case of error
2020
     */
2021
    public static function unsubscribe_user_from_session($session_id, $user_id)
2022
    {
2023
        $session_id = (int) $session_id;
2024
        $user_id = (int) $user_id;
2025
2026
        $tbl_session_rel_course_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
2027
        $tbl_session_rel_course = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
2028
        $tbl_session_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_USER);
2029
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
2030
2031
        $delete_sql = "DELETE FROM $tbl_session_rel_user
2032
		               WHERE
2033
                            session_id = $session_id AND
2034
		                    user_id = $user_id AND
2035
		                    relation_type <> " . SESSION_RELATION_TYPE_RRHH . "";
2036
        $result = Database::query($delete_sql);
2037
        $return = Database::affected_rows($result);
2038
2039
        // Update number of users
2040
        $sql = "UPDATE $tbl_session
2041
                SET nbr_users = nbr_users - $return
2042
                WHERE id = $session_id ";
2043
        Database::query($sql);
2044
2045
        // Get the list of courses related to this session
2046
        $course_list = SessionManager::get_course_list_by_session_id($session_id);
2047
2048
        if (!empty($course_list)) {
2049
            foreach ($course_list as $course) {
0 ignored issues
show
Bug introduced by
The expression $course_list of type integer|array is not guaranteed to be traversable. How about adding an additional type check?

There are different options of fixing this problem.

  1. If you want to be on the safe side, you can add an additional type-check:

    $collection = json_decode($data, true);
    if ( ! is_array($collection)) {
        throw new \RuntimeException('$collection must be an array.');
    }
    
    foreach ($collection as $item) { /** ... */ }
    
  2. If you are sure that the expression is traversable, you might want to add a doc comment cast to improve IDE auto-completion and static analysis:

    /** @var array $collection */
    $collection = json_decode($data, true);
    
    foreach ($collection as $item) { /** .. */ }
    
  3. Mark the issue as a false-positive: Just hover the remove button, in the top-right corner of this issue for more options.

Loading history...
2050
                $courseId = $course['id'];
2051
                // Delete user from course
2052
                $sql = "DELETE FROM $tbl_session_rel_course_rel_user
2053
                        WHERE session_id = $session_id AND c_id = $courseId AND user_id = $user_id";
2054
                $result = Database::query($sql);
2055
2056
                Event::addEvent(
2057
                    LOG_SESSION_DELETE_USER_COURSE,
2058
                    LOG_USER_ID,
2059
                    $user_id,
2060
                    api_get_utc_datetime(),
2061
                    api_get_user_id(),
2062
                    $courseId,
2063
                    $session_id
2064
                );
2065
2066
                if (Database::affected_rows($result)) {
2067
                    // Update number of users in this relation
2068
                    $sql = "UPDATE $tbl_session_rel_course SET nbr_users = nbr_users - 1
2069
                            WHERE session_id = $session_id AND c_id = $courseId";
2070
                    Database::query($sql);
2071
                }
2072
            }
2073
        }
2074
2075
        return true;
2076
    }
2077
2078
    /**
2079
     * Subscribes courses to the given session and optionally (default)
2080
     * unsubscribes previous users
2081
     * @author Carlos Vargas from existing code
2082
     * @param	int		$sessionId
2083
     * @param	array	$courseList List of courses int ids
2084
     * @param	bool	$removeExistingCoursesWithUsers Whether to unsubscribe
2085
     * existing courses and users (true, default) or not (false)
2086
     * @param $copyEvaluation from base course to session course
2087
     * @return	void	Nothing, or false on error
2088
     * */
2089
    public static function add_courses_to_session(
2090
        $sessionId,
2091
        $courseList,
2092
        $removeExistingCoursesWithUsers = true,
2093
        $copyEvaluation = false
2094
    ) {
2095
        $sessionId = intval($sessionId);
2096
2097
        if (empty($sessionId) || empty($courseList)) {
2098
            return false;
2099
        }
2100
2101
        $tbl_session_rel_course_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
2102
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
2103
        $tbl_session_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_USER);
2104
        $tbl_session_rel_course = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
2105
2106
        // Get list of courses subscribed to this session
2107
        $sql = "SELECT c_id
2108
                FROM $tbl_session_rel_course
2109
                WHERE session_id = $sessionId";
2110
        $rs = Database::query($sql);
2111
        $existingCourses = Database::store_result($rs);
2112
        $nbr_courses = count($existingCourses);
2113
2114
        // Get list of users subscribed to this session
2115
        $sql = "SELECT user_id
2116
                FROM $tbl_session_rel_user
2117
                WHERE
2118
                    session_id = $sessionId AND
2119
                    relation_type<>" . SESSION_RELATION_TYPE_RRHH;
2120
        $result = Database::query($sql);
2121
        $user_list = Database::store_result($result);
2122
2123
        // Remove existing courses from the session.
2124
        if ($removeExistingCoursesWithUsers === true && !empty($existingCourses)) {
2125
2126
            foreach ($existingCourses as $existingCourse) {
2127
                if (!in_array($existingCourse['c_id'], $courseList)) {
2128
2129
                    $sql = "DELETE FROM $tbl_session_rel_course
2130
                            WHERE
2131
                                c_id = " . $existingCourse['c_id'] . " AND
2132
                                session_id = $sessionId";
2133
                    Database::query($sql);
2134
2135
                    $sql = "DELETE FROM $tbl_session_rel_course_rel_user
2136
                            WHERE
2137
                                c_id = ".$existingCourse['c_id']." AND
2138
                                session_id = $sessionId";
2139
                    Database::query($sql);
2140
2141
                    Event::addEvent(
2142
                        LOG_SESSION_DELETE_COURSE,
2143
                        LOG_COURSE_ID,
2144
                        $existingCourse['c_id'],
2145
                        api_get_utc_datetime(),
2146
                        api_get_user_id(),
2147
                        $existingCourse['c_id'],
2148
                        $sessionId
2149
                    );
2150
2151
                    CourseManager::remove_course_ranking(
2152
                        $existingCourse['c_id'],
2153
                        $sessionId
2154
                    );
2155
2156
                    $nbr_courses--;
2157
                }
2158
            }
2159
        }
2160
2161
        // Pass through the courses list we want to add to the session
2162
        foreach ($courseList as $courseId) {
2163
            $courseInfo = api_get_course_info_by_id($courseId);
2164
2165
            // If course doesn't exists continue!
2166
            if (empty($courseInfo)) {
2167
                continue;
2168
            }
2169
2170
            $exists = false;
2171
            // check if the course we want to add is already subscribed
2172
            foreach ($existingCourses as $existingCourse) {
2173
                if ($courseId == $existingCourse['c_id']) {
2174
                    $exists = true;
2175
                }
2176
            }
2177
2178
            if (!$exists) {
2179
                // Copy gradebook categories and links (from base course)
2180
                // to the new course session
2181
                if ($copyEvaluation) {
2182
                    $cats = Category::load(null, null, $courseInfo['code']);
2183
                    if (!empty($cats)) {
2184
                        $categoryIdList = [];
2185
                        /** @var Category $cat */
2186
                        foreach ($cats as $cat) {
2187
                            $categoryIdList[$cat->get_id()] = $cat->get_id();
2188
                        }
2189
                        $newCategoryIdList = [];
2190
                        foreach ($cats as $cat) {
2191
                            $links = $cat->get_links(null, false, $courseInfo['code'], 0);
2192
2193
                            $cat->set_session_id($sessionId);
2194
                            $oldCategoryId= $cat->get_id();
2195
                            $newId = $cat->add();
2196
                            $newCategoryIdList[$oldCategoryId] = $newId;
2197
2198
                            $parentId = $cat->get_parent_id();
2199
2200
                            if (!empty($parentId)) {
2201
                                $newParentId = $newCategoryIdList[$parentId];
2202
                                $cat->set_parent_id($newParentId);
2203
                                $cat->save();
2204
                            }
2205
2206
                            /** @var AbstractLink $link */
2207
                            foreach ($links as $link) {
2208
                                $newCategoryId = $newCategoryIdList[$link->get_category_id()];
2209
                                $link->set_category_id($newCategoryId);
2210
                                $link->add();
2211
                            }
2212
                        }
2213
2214
                        // Create
2215
                        DocumentManager::generateDefaultCertificate(
2216
                            $courseInfo,
2217
                            true,
2218
                            $sessionId
2219
                        );
2220
                    }
2221
                }
2222
2223
                // If the course isn't subscribed yet
2224
                $sql = "INSERT INTO $tbl_session_rel_course (session_id, c_id)
2225
                        VALUES ($sessionId, $courseId)";
2226
                Database::query($sql);
2227
2228
                Event::addEvent(
2229
                    LOG_SESSION_ADD_COURSE,
2230
                    LOG_COURSE_ID,
2231
                    $courseId,
2232
                    api_get_utc_datetime(),
2233
                    api_get_user_id(),
2234
                    $courseId,
2235
                    $sessionId
2236
                );
2237
2238
                // We add the current course in the existing courses array,
2239
                // to avoid adding another time the current course
2240
                $existingCourses[] = array('c_id' => $courseId);
2241
                $nbr_courses++;
2242
2243
                // subscribe all the users from the session to this course inside the session
2244
                $nbr_users = 0;
2245 View Code Duplication
                foreach ($user_list as $enreg_user) {
2246
                    $enreg_user_id = intval($enreg_user['user_id']);
2247
                    $sql = "INSERT IGNORE INTO $tbl_session_rel_course_rel_user (session_id, c_id, user_id)
2248
                            VALUES ($sessionId, $courseId, $enreg_user_id)";
2249
                    $result = Database::query($sql);
2250
2251
                    Event::addEvent(
2252
                        LOG_SESSION_ADD_USER_COURSE,
2253
                        LOG_USER_ID,
2254
                        $enreg_user_id,
2255
                        api_get_utc_datetime(),
2256
                        api_get_user_id(),
2257
                        $courseId,
2258
                        $sessionId
2259
                    );
2260
2261
                    if (Database::affected_rows($result)) {
2262
                        $nbr_users++;
2263
                    }
2264
                }
2265
                $sql = "UPDATE $tbl_session_rel_course
2266
                        SET nbr_users = $nbr_users
2267
                        WHERE session_id = $sessionId AND c_id = $courseId";
2268
                Database::query($sql);
2269
            }
2270
        }
2271
2272
        $sql = "UPDATE $tbl_session
2273
                SET nbr_courses = $nbr_courses
2274
                WHERE id = $sessionId";
2275
        Database::query($sql);
2276
    }
2277
2278
    /**
2279
     * Unsubscribe course from a session
2280
     *
2281
     * @param int Session id
2282
     * @param int Course id
2283
     * @return bool True in case of success, false otherwise
2284
     */
2285
    public static function unsubscribe_course_from_session($session_id, $course_id)
2286
    {
2287
        $session_id = (int) $session_id;
2288
        $course_id = (int) $course_id;
2289
2290
        $tbl_session_rel_course = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
2291
        $tbl_session_rel_course_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
2292
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
2293
2294
        // Get course code
2295
        $course_code = CourseManager::get_course_code_from_course_id($course_id);
2296
        $course_id = intval($course_id);
2297
2298
        if (empty($course_code)) {
2299
            return false;
2300
        }
2301
2302
        // Unsubscribe course
2303
        $sql = "DELETE FROM $tbl_session_rel_course
2304
                WHERE c_id = $course_id AND session_id = $session_id";
2305
        $result = Database::query($sql);
2306
        $nb_affected = Database::affected_rows($result);
2307
2308
        $sql = "DELETE FROM $tbl_session_rel_course_rel_user
2309
                WHERE c_id = $course_id AND session_id = $session_id";
2310
        Database::query($sql);
2311
2312
        Event::addEvent(
2313
            LOG_SESSION_DELETE_COURSE,
2314
            LOG_COURSE_ID,
2315
            $course_id,
2316
            api_get_utc_datetime(),
2317
            api_get_user_id(),
2318
            $course_id,
2319
            $session_id
2320
        );
2321
2322
        if ($nb_affected > 0) {
2323
            // Update number of courses in the session
2324
            $sql = "UPDATE $tbl_session SET nbr_courses= nbr_courses - $nb_affected
2325
                    WHERE id = $session_id";
2326
            Database::query($sql);
2327
            return true;
2328
        } else {
2329
            return false;
2330
        }
2331
    }
2332
2333
    /**
2334
     * Creates a new extra field for a given session
2335
     * @param	string	$variable Field's internal variable name
2336
     * @param	int		$fieldType Field's type
2337
     * @param	string	$displayText Field's language var name
2338
     * @return int     new extra field id
2339
     */
2340 View Code Duplication
    public static function create_session_extra_field($variable, $fieldType, $displayText)
2341
    {
2342
        $extraField = new ExtraField('session');
2343
        $params = [
2344
            'variable' => $variable,
2345
            'field_type' => $fieldType,
2346
            'display_text' => $displayText,
2347
        ];
2348
2349
        return $extraField->save($params);
2350
    }
2351
2352
    /**
2353
     * Update an extra field value for a given session
2354
     * @param	integer	Course ID
2355
     * @param	string	Field variable name
2356
     * @param	string	Field value
2357
     * @return	boolean	true if field updated, false otherwise
2358
     */
2359 View Code Duplication
    public static function update_session_extra_field_value($sessionId, $variable, $value = '')
2360
    {
2361
        $extraFieldValue = new ExtraFieldValue('session');
2362
        $params = [
2363
            'item_id' => $sessionId,
2364
            'variable' => $variable,
2365
            'value' => $value,
2366
        ];
2367
        $extraFieldValue->save($params);
2368
    }
2369
2370
    /**
2371
     * Checks the relationship between a session and a course.
2372
     * @param int $session_id
2373
     * @param int $courseId
2374
     * @return bool Returns TRUE if the session and the course are related, FALSE otherwise.
2375
     * */
2376 View Code Duplication
    public static function relation_session_course_exist($session_id, $courseId)
2377
    {
2378
        $tbl_session_course = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
2379
        $return_value = false;
2380
        $sql = "SELECT c_id FROM $tbl_session_course
2381
                WHERE
2382
                  session_id = " . intval($session_id) . " AND
2383
                  c_id = " . intval($courseId) . "";
2384
        $result = Database::query($sql);
2385
        $num = Database::num_rows($result);
2386
        if ($num > 0) {
2387
            $return_value = true;
2388
        }
2389
        return $return_value;
2390
    }
2391
2392
    /**
2393
     * Get the session information by name
2394
     * @param string session name
2395
     * @return mixed false if the session does not exist, array if the session exist
2396
     * */
2397
    public static function get_session_by_name($session_name)
2398
    {
2399
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
2400
        $session_name = trim($session_name);
2401
        if (empty($session_name)) {
2402
            return false;
2403
        }
2404
2405
        $sql = 'SELECT *
2406
		        FROM ' . $tbl_session . '
2407
		        WHERE name = "' . Database::escape_string($session_name) . '"';
2408
        $result = Database::query($sql);
2409
        $num = Database::num_rows($result);
2410
        if ($num > 0) {
2411
            return Database::fetch_array($result);
2412
        } else {
2413
            return false;
2414
        }
2415
    }
2416
2417
    /**
2418
     * Create a session category
2419
     * @author Jhon Hinojosa <[email protected]>, from existing code
2420
     * @param	string 		name
2421
     * @param 	integer		year_start
2422
     * @param 	integer		month_start
2423
     * @param 	integer		day_start
2424
     * @param 	integer		year_end
2425
     * @param 	integer		month_end
2426
     * @param 	integer		day_end
2427
     * @return $id_session;
0 ignored issues
show
Documentation introduced by
The doc-type $id_session; could not be parsed: Unknown type name "$id_session" at position 0. (view supported doc-types)

This check marks PHPDoc comments that could not be parsed by our parser. To see which comment annotations we can parse, please refer to our documentation on supported doc-types.

Loading history...
2428
     * */
2429
    public static function create_category_session(
2430
        $sname,
2431
        $syear_start,
2432
        $smonth_start,
2433
        $sday_start,
2434
        $syear_end,
2435
        $smonth_end,
2436
        $sday_end
2437
    ) {
2438
        $tbl_session_category = Database::get_main_table(TABLE_MAIN_SESSION_CATEGORY);
2439
        $name = trim($sname);
2440
        $year_start = intval($syear_start);
2441
        $month_start = intval($smonth_start);
2442
        $day_start = intval($sday_start);
2443
        $year_end = intval($syear_end);
2444
        $month_end = intval($smonth_end);
2445
        $day_end = intval($sday_end);
2446
2447
        $date_start = "$year_start-" . (($month_start < 10) ? "0$month_start" : $month_start) . "-" . (($day_start < 10) ? "0$day_start" : $day_start);
2448
        $date_end = "$year_end-" . (($month_end < 10) ? "0$month_end" : $month_end) . "-" . (($day_end < 10) ? "0$day_end" : $day_end);
2449
2450 View Code Duplication
        if (empty($name)) {
2451
            $msg = get_lang('SessionCategoryNameIsRequired');
2452
            return $msg;
2453
        } elseif (!$month_start || !$day_start || !$year_start || !checkdate($month_start, $day_start, $year_start)) {
2454
            $msg = get_lang('InvalidStartDate');
2455
            return $msg;
2456
        } elseif (!$month_end && !$day_end && !$year_end) {
2457
            $date_end = "null";
2458
        } elseif (!$month_end || !$day_end || !$year_end || !checkdate($month_end, $day_end, $year_end)) {
2459
            $msg = get_lang('InvalidEndDate');
2460
            return $msg;
2461
        } elseif ($date_start >= $date_end) {
2462
            $msg = get_lang('StartDateShouldBeBeforeEndDate');
2463
            return $msg;
2464
        }
2465
2466
        $access_url_id = api_get_current_access_url_id();
2467
        $params = [
2468
            'name' => $name,
2469
            'date_start' => $date_start,
2470
            'date_end' => $date_end,
2471
            'access_url_id' => $access_url_id
2472
        ];
2473
        $id_session = Database::insert($tbl_session_category, $params);
2474
2475
        // Add event to system log
2476
        $user_id = api_get_user_id();
2477
        Event::addEvent(
2478
            LOG_SESSION_CATEGORY_CREATE,
2479
            LOG_SESSION_CATEGORY_ID,
2480
            $id_session,
0 ignored issues
show
Security Bug introduced by
It seems like $id_session defined by \Database::insert($tbl_session_category, $params) on line 2473 can also be of type false; however, Event::addEvent() does only seem to accept string, did you maybe forget to handle an error condition?

This check looks for type mismatches where the missing type is false. This is usually indicative of an error condtion.

Consider the follow example

<?php

function getDate($date)
{
    if ($date !== null) {
        return new DateTime($date);
    }

    return false;
}

This function either returns a new DateTime object or false, if there was an error. This is a typical pattern in PHP programming to show that an error has occurred without raising an exception. The calling code should check for this returned false before passing on the value to another function or method that may not be able to handle a false.

Loading history...
2481
            api_get_utc_datetime(),
2482
            $user_id
2483
        );
2484
        return $id_session;
2485
    }
2486
2487
    /**
2488
     * Edit a sessions categories
2489
     * @author Jhon Hinojosa <[email protected]>,from existing code
2490
     * @param	integer		id
2491
     * @param	string 		name
2492
     * @param 	integer		year_start
2493
     * @param 	integer		month_start
2494
     * @param 	integer		day_start
2495
     * @param 	integer		year_end
2496
     * @param 	integer		month_end
2497
     * @param 	integer		day_end
2498
     * @return $id;
0 ignored issues
show
Documentation introduced by
The doc-type $id; could not be parsed: Unknown type name "$id" at position 0. (view supported doc-types)

This check marks PHPDoc comments that could not be parsed by our parser. To see which comment annotations we can parse, please refer to our documentation on supported doc-types.

Loading history...
2499
     * The parameter id is a primary key
2500
     * */
2501
    public static function edit_category_session(
2502
        $id,
2503
        $sname,
2504
        $syear_start,
2505
        $smonth_start,
2506
        $sday_start,
2507
        $syear_end,
2508
        $smonth_end,
2509
        $sday_end
2510
    ) {
2511
        $tbl_session_category = Database::get_main_table(TABLE_MAIN_SESSION_CATEGORY);
2512
        $name = trim($sname);
2513
        $year_start = intval($syear_start);
2514
        $month_start = intval($smonth_start);
2515
        $day_start = intval($sday_start);
2516
        $year_end = intval($syear_end);
2517
        $month_end = intval($smonth_end);
2518
        $day_end = intval($sday_end);
2519
        $id = intval($id);
2520
        $date_start = "$year_start-" . (($month_start < 10) ? "0$month_start" : $month_start) . "-" . (($day_start < 10) ? "0$day_start" : $day_start);
2521
        $date_end = "$year_end-" . (($month_end < 10) ? "0$month_end" : $month_end) . "-" . (($day_end < 10) ? "0$day_end" : $day_end);
2522
2523 View Code Duplication
        if (empty($name)) {
2524
            $msg = get_lang('SessionCategoryNameIsRequired');
2525
            return $msg;
2526
        } elseif (!$month_start || !$day_start || !$year_start || !checkdate($month_start, $day_start, $year_start)) {
2527
            $msg = get_lang('InvalidStartDate');
2528
            return $msg;
2529
        } elseif (!$month_end && !$day_end && !$year_end) {
2530
            $date_end = null;
2531
        } elseif (!$month_end || !$day_end || !$year_end || !checkdate($month_end, $day_end, $year_end)) {
2532
            $msg = get_lang('InvalidEndDate');
2533
            return $msg;
2534
        } elseif ($date_start >= $date_end) {
2535
            $msg = get_lang('StartDateShouldBeBeforeEndDate');
2536
            return $msg;
2537
        }
2538
        if ($date_end <> null) {
0 ignored issues
show
Bug introduced by
It seems like you are loosely comparing $date_end of type null|string against null; this is ambiguous if the string can be empty. Consider using a strict comparison !== instead.
Loading history...
2539
            $sql = "UPDATE $tbl_session_category
2540
                    SET
2541
                        name = '" . Database::escape_string($name) . "',
2542
                        date_start = '$date_start' ,
2543
                        date_end = '$date_end'
2544
                    WHERE id= $id";
2545
        } else {
2546
            $sql = "UPDATE $tbl_session_category SET
2547
                        name = '" . Database::escape_string($name) . "',
2548
                        date_start = '$date_start',
2549
                        date_end = NULL
2550
                    WHERE id= $id";
2551
        }
2552
        $result = Database::query($sql);
2553
        return ($result ? true : false);
2554
    }
2555
2556
    /**
2557
     * Delete sessions categories
2558
     * @author Jhon Hinojosa <[email protected]>, from existing code
2559
     * @param	array	id_checked
2560
     * @param	bool	include delete session
2561
     * @param	bool	optional, true if the function is called by a webservice, false otherwise.
2562
     * @return	void	Nothing, or false on error
2563
     * The parameters is a array to delete sessions
2564
     * */
2565
    public static function delete_session_category($id_checked, $delete_session = false, $from_ws = false)
2566
    {
2567
        $tbl_session_category = Database::get_main_table(TABLE_MAIN_SESSION_CATEGORY);
2568
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
2569
        if (is_array($id_checked)) {
2570
            $id_checked = Database::escape_string(implode(',', $id_checked));
2571
        } else {
2572
            $id_checked = intval($id_checked);
2573
        }
2574
2575
        //Setting session_category_id to 0
2576
        $sql = "UPDATE $tbl_session SET session_category_id = 0
2577
                WHERE session_category_id IN (" . $id_checked . ")";
2578
        Database::query($sql);
2579
2580
        $sql = "SELECT id FROM $tbl_session WHERE session_category_id IN (" . $id_checked . ")";
2581
        $result = Database::query($sql);
2582
        while ($rows = Database::fetch_array($result)) {
2583
            $session_id = $rows['id'];
2584
            if ($delete_session) {
2585
                if ($from_ws) {
2586
                    SessionManager::delete($session_id, true);
2587
                } else {
2588
                    SessionManager::delete($session_id);
2589
                }
2590
            }
2591
        }
2592
        $sql = "DELETE FROM $tbl_session_category WHERE id IN (" . $id_checked . ")";
2593
        Database::query($sql);
2594
2595
        // Add event to system log
2596
        $user_id = api_get_user_id();
2597
        Event::addEvent(
2598
            LOG_SESSION_CATEGORY_DELETE,
2599
            LOG_SESSION_CATEGORY_ID,
2600
            $id_checked,
2601
            api_get_utc_datetime(),
2602
            $user_id
2603
        );
2604
2605
        return true;
2606
    }
2607
2608
    /**
2609
     * Get a list of sessions of which the given conditions match with an = 'cond'
2610
     * @param  array $conditions a list of condition example :
2611
     * array('status' => STUDENT) or
2612
     * array('s.name' => array('operator' => 'LIKE', value = '%$needle%'))
2613
     * @param  array $order_by a list of fields on which sort
2614
     * @return array An array with all sessions of the platform.
2615
     * @todo   optional course code parameter, optional sorting parameters...
2616
     */
2617
    public static function get_sessions_list($conditions = array(), $order_by = array(), $from = null, $to = null)
2618
    {
2619
        $session_table = Database::get_main_table(TABLE_MAIN_SESSION);
2620
        $session_category_table = Database::get_main_table(TABLE_MAIN_SESSION_CATEGORY);
2621
        $user_table = Database::get_main_table(TABLE_MAIN_USER);
2622
        $table_access_url_rel_session = Database::get_main_table(TABLE_MAIN_ACCESS_URL_REL_SESSION);
2623
        $session_course_table = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
2624
        $course_table = Database::get_main_table(TABLE_MAIN_COURSE);
2625
        $access_url_id = api_get_current_access_url_id();
2626
        $return_array = array();
2627
2628
        $sql_query = " SELECT
2629
                    s.id,
2630
                    s.name,
2631
                    s.nbr_courses,
2632
                    s.access_start_date,
2633
                    s.access_end_date,
2634
                    u.firstname,
2635
                    u.lastname,
2636
                    sc.name as category_name,
2637
                    s.promotion_id
2638
				FROM $session_table s
2639
				INNER JOIN $user_table u ON s.id_coach = u.user_id
2640
				INNER JOIN $table_access_url_rel_session ar ON ar.session_id = s.id
2641
				LEFT JOIN  $session_category_table sc ON s.session_category_id = sc.id
2642
				LEFT JOIN $session_course_table sco ON (sco.session_id = s.id)
2643
				INNER JOIN $course_table c ON sco.c_id = c.id
2644
				WHERE ar.access_url_id = $access_url_id ";
2645
2646
        $availableFields = array(
2647
            's.id',
2648
            's.name',
2649
            'c.id'
2650
        );
2651
2652
        $availableOperator = array(
2653
            'like',
2654
            '>=',
2655
            '<=',
2656
            '=',
2657
        );
2658
2659
        if (count($conditions) > 0) {
2660
            foreach ($conditions as $field => $options) {
2661
                $operator = strtolower($options['operator']);
2662
                $value = Database::escape_string($options['value']);
2663
                $sql_query .= ' AND ';
2664
                if (in_array($field, $availableFields) && in_array($operator, $availableOperator)) {
2665
                    $sql_query .= $field . " $operator '" . $value . "'";
2666
                }
2667
            }
2668
        }
2669
2670
        $orderAvailableList = array('name');
2671
2672
        if (count($order_by) > 0) {
2673
            $order = null;
2674
            $direction = null;
2675
            if (isset($order_by[0]) && in_array($order_by[0], $orderAvailableList)) {
2676
                $order = $order_by[0];
2677
            }
2678
            if (isset($order_by[1]) && in_array(strtolower($order_by[1]), array('desc', 'asc'))) {
2679
                $direction = $order_by[1];
2680
            }
2681
2682
            if (!empty($order)) {
2683
                $sql_query .= " ORDER BY $order $direction ";
2684
            }
2685
        }
2686
2687
        if (!is_null($from) && !is_null($to)) {
2688
            $to = intval($to);
2689
            $from = intval($from);
2690
            $sql_query .= "LIMIT $from, $to";
2691
        }
2692
2693
        $sql_result = Database::query($sql_query);
2694
        if (Database::num_rows($sql_result) > 0) {
2695
            while ($result = Database::fetch_array($sql_result)) {
2696
                $return_array[$result['id']] = $result;
2697
            }
2698
        }
2699
2700
        return $return_array;
2701
    }
2702
2703
    /**
2704
     * Get the session category information by id
2705
     * @param string session category ID
2706
     * @return mixed false if the session category does not exist, array if the session category exists
2707
     */
2708
    public static function get_session_category($id)
2709
    {
2710
        $tbl_session_category = Database::get_main_table(TABLE_MAIN_SESSION_CATEGORY);
2711
        $id = intval($id);
2712
        $sql = "SELECT id, name, date_start, date_end
2713
                FROM $tbl_session_category
2714
                WHERE id= $id";
2715
        $result = Database::query($sql);
2716
        $num = Database::num_rows($result);
2717
        if ($num > 0) {
2718
            return Database::fetch_array($result);
2719
        } else {
2720
            return false;
2721
        }
2722
    }
2723
2724
    /**
2725
     * Get all session categories (filter by access_url_id)
2726
     * @return mixed false if the session category does not exist, array if the session category exists
2727
     */
2728
    public static function get_all_session_category()
2729
    {
2730
        $tbl_session_category = Database::get_main_table(TABLE_MAIN_SESSION_CATEGORY);
2731
        $id = api_get_current_access_url_id();
2732
        $sql = 'SELECT * FROM ' . $tbl_session_category . '
2733
                WHERE access_url_id = ' . $id . '
2734
                ORDER BY name ASC';
2735
        $result = Database::query($sql);
2736
        if (Database::num_rows($result) > 0) {
2737
            $data = Database::store_result($result, 'ASSOC');
2738
            return $data;
2739
        } else {
2740
            return false;
2741
        }
2742
    }
2743
2744
    /**
2745
     * Assign a coach to course in session with status = 2
2746
     * @param int  $user_id
2747
     * @param int  $session_id
2748
     * @param int  $courseId
2749
     * @param bool $nocoach optional, if is true the user don't be a coach now,
2750
     * otherwise it'll assign a coach
2751
     * @return bool true if there are affected rows, otherwise false
2752
     */
2753
    public static function set_coach_to_course_session(
2754
        $user_id,
2755
        $session_id = 0,
2756
        $courseId = 0,
2757
        $nocoach = false
2758
    ) {
2759
        // Definition of variables
2760
        $user_id = intval($user_id);
2761
2762
        if (!empty($session_id)) {
2763
            $session_id = intval($session_id);
2764
        } else {
2765
            $session_id = api_get_session_id();
2766
        }
2767
2768
        if (!empty($courseId)) {
2769
            $courseId = intval($courseId);
2770
        } else {
2771
            $courseId = api_get_course_id();
2772
        }
2773
2774
        // Table definition
2775
        $tbl_session_rel_course_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
2776
        $tbl_session_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_USER);
2777
        $tbl_user = Database::get_main_table(TABLE_MAIN_USER);
2778
2779
        // check if user is a teacher
2780
        $sql = "SELECT * FROM $tbl_user
2781
                WHERE status = 1 AND user_id = $user_id";
2782
2783
        $rs_check_user = Database::query($sql);
2784
2785
        if (Database::num_rows($rs_check_user) > 0) {
2786
            if ($nocoach) {
2787
                // check if user_id exists in session_rel_user (if the user is
2788
                // subscribed to the session in any manner)
2789
                $sql = "SELECT user_id FROM $tbl_session_rel_user
2790
                        WHERE
2791
                            session_id = $session_id AND
2792
                            user_id = $user_id";
2793
                $res = Database::query($sql);
2794
2795 View Code Duplication
                if (Database::num_rows($res) > 0) {
2796
                    // The user is already subscribed to the session. Change the
2797
                    // record so the user is NOT a coach for this course anymore
2798
                    // and then exit
2799
                    $sql = "UPDATE $tbl_session_rel_course_rel_user
2800
                            SET status = 0
2801
                            WHERE
2802
                                session_id = $session_id AND
2803
                                c_id = $courseId AND
2804
                                user_id = $user_id ";
2805
                    $result = Database::query($sql);
2806
                    if (Database::affected_rows($result) > 0)
2807
                        return true;
2808
                    else
2809
                        return false;
2810
                } else {
2811
                    // The user is not subscribed to the session, so make sure
2812
                    // he isn't subscribed to a course in this session either
2813
                    // and then exit
2814
                    $sql = "DELETE FROM $tbl_session_rel_course_rel_user
2815
                            WHERE
2816
                                session_id = $session_id AND
2817
                                c_id = $courseId AND
2818
                                user_id = $user_id ";
2819
                    $result = Database::query($sql);
2820
                    if (Database::affected_rows($result) > 0)
2821
                        return true;
2822
                    else
2823
                        return false;
2824
                }
2825
            } else {
2826
                // Assign user as a coach to course
2827
                // First check if the user is registered to the course
2828
                $sql = "SELECT user_id FROM $tbl_session_rel_course_rel_user
2829
                        WHERE
2830
                            session_id = $session_id AND
2831
                            c_id = $courseId AND
2832
                            user_id = $user_id";
2833
                $rs_check = Database::query($sql);
2834
2835
                // Then update or insert.
2836 View Code Duplication
                if (Database::num_rows($rs_check) > 0) {
2837
                    $sql = "UPDATE $tbl_session_rel_course_rel_user SET status = 2
2838
					        WHERE
2839
					            session_id = $session_id AND
2840
					            c_id = $courseId AND
2841
					            user_id = $user_id ";
2842
                    $result = Database::query($sql);
2843
                    if (Database::affected_rows($result) > 0) {
2844
                        return true;
2845
                    } else {
2846
                        return false;
2847
                    }
2848
                } else {
2849
                    $sql = "INSERT INTO $tbl_session_rel_course_rel_user(session_id, c_id, user_id, status)
2850
                            VALUES($session_id, $courseId, $user_id, 2)";
2851
                    $result = Database::query($sql);
2852
                    if (Database::affected_rows($result) > 0) {
2853
                        return true;
2854
                    } else {
2855
                        return false;
2856
                    }
2857
                }
2858
            }
2859
        } else {
2860
            return false;
2861
        }
2862
    }
2863
2864
    /**
2865
     * Subscribes sessions to human resource manager (Dashboard feature)
2866
     * @param array $userInfo Human Resource Manager info
2867
     * @param array $sessions_list Sessions id
2868
     * @param bool $sendEmail
2869
     * @param bool $removeOldConnections
2870
     * @return int
2871
     * */
2872
    public static function suscribe_sessions_to_hr_manager(
2873
        $userInfo,
2874
        $sessions_list,
2875
        $sendEmail = false,
2876
        $removeOldConnections = true
2877
    ) {
2878
        // Database Table Definitions
2879
        $tbl_session_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_USER);
2880
        $tbl_session_rel_access_url = Database::get_main_table(TABLE_MAIN_ACCESS_URL_REL_SESSION);
2881
2882
        if (empty($userInfo)) {
2883
2884
            return 0;
2885
        }
2886
2887
        $userId = $userInfo['user_id'];
2888
2889
        // Only subscribe DRH users.
2890
        $rolesAllowed = array(
2891
            DRH,
2892
            SESSIONADMIN,
2893
            PLATFORM_ADMIN,
2894
            COURSE_TUTOR
2895
        );
2896
        $isAdmin = api_is_platform_admin_by_id($userInfo['user_id']);
2897
        if (!$isAdmin && !in_array($userInfo['status'], $rolesAllowed)) {
2898
2899
            return 0;
2900
        }
2901
2902
        $affected_rows = 0;
2903
2904
        // Deleting assigned sessions to hrm_id.
2905
        if ($removeOldConnections) {
2906
            if (api_is_multiple_url_enabled()) {
2907
                $sql = "SELECT session_id
2908
                        FROM $tbl_session_rel_user s
2909
                        INNER JOIN $tbl_session_rel_access_url a ON (a.session_id = s.session_id)
2910
                        WHERE
2911
                            s.user_id = $userId AND
2912
                            relation_type=" . SESSION_RELATION_TYPE_RRHH . " AND
2913
                            access_url_id = " . api_get_current_access_url_id() . "";
2914
            } else {
2915
                $sql = "SELECT session_id FROM $tbl_session_rel_user s
2916
                        WHERE user_id = $userId AND relation_type=" . SESSION_RELATION_TYPE_RRHH . "";
2917
            }
2918
            $result = Database::query($sql);
2919
2920 View Code Duplication
            if (Database::num_rows($result) > 0) {
2921
                while ($row = Database::fetch_array($result)) {
2922
                    $sql = "DELETE FROM $tbl_session_rel_user
2923
                            WHERE
2924
                                session_id = {$row['session_id']} AND
2925
                                user_id = $userId AND
2926
                                relation_type=" . SESSION_RELATION_TYPE_RRHH . " ";
2927
                    Database::query($sql);
2928
                }
2929
            }
2930
        }
2931
        // Inserting new sessions list.
2932
        if (!empty($sessions_list) && is_array($sessions_list)) {
2933
2934
            foreach ($sessions_list as $session_id) {
2935
                $session_id = intval($session_id);
2936
                $sql = "INSERT IGNORE INTO $tbl_session_rel_user (session_id, user_id, relation_type, registered_at)
2937
                        VALUES (
2938
                            $session_id,
2939
                            $userId,
2940
                            '" . SESSION_RELATION_TYPE_RRHH . "',
2941
                            '" . api_get_utc_datetime() . "'
2942
                        )";
2943
2944
                Database::query($sql);
2945
                $affected_rows++;
2946
            }
2947
        }
2948
2949
        return $affected_rows;
2950
    }
2951
2952
    /**
2953
     * @param int $sessionId
2954
     * @return array
2955
     */
2956
    public static function getDrhUsersInSession($sessionId)
2957
    {
2958
        return self::get_users_by_session($sessionId, SESSION_RELATION_TYPE_RRHH);
2959
    }
2960
2961
    /**
2962
     * @param int $userId
2963
     * @param int $sessionId
2964
     * @return array
2965
     */
2966
    public static function getSessionFollowedByDrh($userId, $sessionId)
2967
    {
2968
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
2969
        $tbl_session_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_USER);
2970
        $tbl_session_rel_access_url = Database::get_main_table(TABLE_MAIN_ACCESS_URL_REL_SESSION);
2971
2972
        $userId = intval($userId);
2973
        $sessionId = intval($sessionId);
2974
2975
        $select = " SELECT * ";
2976
        if (api_is_multiple_url_enabled()) {
2977
            $sql = " $select FROM $tbl_session s
2978
                    INNER JOIN $tbl_session_rel_user sru ON (sru.session_id = s.id)
2979
                    LEFT JOIN $tbl_session_rel_access_url a ON (s.id = a.session_id)
2980
                    WHERE
2981
                        sru.user_id = '$userId' AND
2982
                        sru.session_id = '$sessionId' AND
2983
                        sru.relation_type = '" . SESSION_RELATION_TYPE_RRHH . "' AND
2984
                        access_url_id = " . api_get_current_access_url_id() . "
2985
                        ";
2986
        } else {
2987
            $sql = "$select FROM $tbl_session s
2988
                     INNER JOIN $tbl_session_rel_user sru
2989
                     ON
2990
                        sru.session_id = s.id AND
2991
                        sru.user_id = '$userId' AND
2992
                        sru.session_id = '$sessionId' AND
2993
                        sru.relation_type = '" . SESSION_RELATION_TYPE_RRHH . "'
2994
                    ";
2995
        }
2996
2997
        $result = Database::query($sql);
2998
        if (Database::num_rows($result)) {
2999
            $row = Database::fetch_array($result, 'ASSOC');
3000
            $row['course_list'] = self::get_course_list_by_session_id($sessionId);
3001
3002
            return $row;
3003
        }
3004
3005
        return array();
3006
    }
3007
3008
    /**
3009
     * Get sessions followed by human resources manager
3010
     * @param int $userId
3011
     * @param int $start
3012
     * @param int $limit
3013
     * @param bool $getCount
3014
     * @param bool $getOnlySessionId
3015
     * @param bool $getSql
3016
     * @param string $orderCondition
3017
     * @param string $description
3018
     *
3019
     * @return array sessions
3020
     */
3021
    public static function get_sessions_followed_by_drh(
3022
        $userId,
3023
        $start = null,
3024
        $limit = null,
3025
        $getCount = false,
3026
        $getOnlySessionId = false,
3027
        $getSql = false,
3028
        $orderCondition = null,
3029
        $keyword = '',
3030
        $description = ''
3031
    ) {
3032
        return self::getSessionsFollowedByUser(
3033
            $userId,
3034
            DRH,
3035
            $start,
3036
            $limit,
3037
            $getCount,
3038
            $getOnlySessionId,
3039
            $getSql,
3040
            $orderCondition,
3041
            $keyword,
3042
            $description
3043
        );
3044
    }
3045
3046
    /**
3047
     * Get sessions followed by human resources manager
3048
     * @param int $userId
3049
     * @param int $start
3050
     * @param int $limit
3051
     * @param bool $getCount
3052
     * @param bool $getOnlySessionId
3053
     * @param bool $getSql
3054
     * @param string $orderCondition
3055
     * @param string $keyword
3056
     * @param string $description
3057
     * @return array sessions
3058
     */
3059
    public static function getSessionsFollowedByUser(
3060
        $userId,
3061
        $status = null,
3062
        $start = null,
3063
        $limit = null,
3064
        $getCount = false,
3065
        $getOnlySessionId = false,
3066
        $getSql = false,
3067
        $orderCondition = null,
3068
        $keyword = '',
3069
        $description = ''
3070
    ) {
3071
        // Database Table Definitions
3072
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
3073
        $tbl_session_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_USER);
3074
        $tbl_session_rel_course_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
3075
        $tbl_session_rel_access_url = Database::get_main_table(TABLE_MAIN_ACCESS_URL_REL_SESSION);
3076
3077
        $userId = intval($userId);
3078
3079
        $select = " SELECT DISTINCT * ";
3080
3081
        if ($getCount) {
3082
            $select = " SELECT count(DISTINCT(s.id)) as count ";
3083
        }
3084
3085
        if ($getOnlySessionId) {
3086
            $select = " SELECT DISTINCT(s.id) ";
3087
        }
3088
3089
        $limitCondition = null;
3090 View Code Duplication
        if (!empty($start) && !empty($limit)) {
3091
            $limitCondition = " LIMIT " . intval($start) . ", " . intval($limit);
3092
        }
3093
3094
        if (empty($orderCondition)) {
3095
            $orderCondition = " ORDER BY s.name ";
3096
        }
3097
3098
        $whereConditions = null;
3099
        $sessionCourseConditions = null;
3100
        $sessionConditions = null;
3101
        $sessionQuery = null;
3102
        $courseSessionQuery = null;
3103
3104
        switch ($status) {
3105
            case DRH:
3106
                $sessionQuery = "SELECT sru.session_id
3107
                                 FROM
3108
                                 $tbl_session_rel_user sru
3109
                                 WHERE
3110
                                    sru.relation_type = '".SESSION_RELATION_TYPE_RRHH."' AND
3111
                                    sru.user_id = $userId";
3112
                break;
3113
            case COURSEMANAGER:
3114
                $courseSessionQuery = "
3115
                    SELECT scu.session_id as id
3116
                    FROM $tbl_session_rel_course_rel_user scu
3117
                    WHERE (scu.status = 2 AND scu.user_id = $userId)";
3118
3119
                $whereConditions = " OR (s.id_coach = $userId) ";
3120
                break;
3121
            default:
3122
                $sessionQuery = "SELECT sru.session_id
3123
                                 FROM
3124
                                 $tbl_session_rel_user sru
3125
                                 WHERE
3126
                                    sru.user_id = $userId";
3127
                break;
3128
        }
3129
3130
        $keywordCondition = '';
3131 View Code Duplication
        if (!empty($keyword)) {
3132
            $keyword = Database::escape_string($keyword);
3133
            $keywordCondition = " AND (s.name LIKE '%$keyword%' ) ";
3134
3135
            if (!empty($description)) {
3136
                $description = Database::escape_string($description);
3137
                $keywordCondition = " AND (s.name LIKE '%$keyword%' OR s.description LIKE '%$description%' ) ";
3138
            }
3139
        }
3140
3141
        $whereConditions .= $keywordCondition;
3142
3143
        $subQuery = $sessionQuery.$courseSessionQuery;
3144
3145
        $sql = " $select FROM $tbl_session s
3146
                INNER JOIN $tbl_session_rel_access_url a ON (s.id = a.session_id)
3147
                WHERE
3148
                    access_url_id = ".api_get_current_access_url_id()." AND
3149
                    s.id IN (
3150
                        $subQuery
3151
                    )
3152
                    $whereConditions
3153
                    $orderCondition
3154
                    $limitCondition";
3155
3156
        if ($getSql) {
3157
            return $sql;
3158
        }
3159
3160
        $result = Database::query($sql);
3161
3162
        if ($getCount) {
3163
            $row = Database::fetch_array($result);
3164
            return $row['count'];
3165
        }
3166
3167
        $sessions = array();
3168
        if (Database::num_rows($result) > 0) {
3169
            $sysUploadPath = api_get_path(SYS_UPLOAD_PATH). 'sessions/';
3170
            $webUploadPath = api_get_path(WEB_UPLOAD_PATH). 'sessions/';
3171
            $imgPath = Display::returnIconPath('session_default_small.png');
3172
3173
            $tableExtraFields = Database::get_main_table(TABLE_EXTRA_FIELD);
3174
            $sql = "SELECT id FROM " . $tableExtraFields . "
3175
                    WHERE extra_field_type = 3 AND variable='image'";
3176
            $resultField = Database::query($sql);
3177
            $imageFieldId = Database::fetch_assoc($resultField);
3178
3179
            while ($row = Database::fetch_array($result)) {
3180
3181
                $row['image'] =  null;
3182
                $sessionImage = $sysUploadPath . $imageFieldId['id'] . '_' . $row['id'] . '.png';
3183
3184
                if (is_file($sessionImage)) {
3185
                    $sessionImage = $webUploadPath . $imageFieldId['id'] . '_' . $row['id'] . '.png';
3186
                    $row['image'] = $sessionImage;
3187
                } else {
3188
                    $row['image'] =  $imgPath;
3189
                }
3190
3191
                $sessions[$row['id']] = $row;
3192
3193
            }
3194
        }
3195
3196
        return $sessions;
3197
    }
3198
3199
    /**
3200
     * Gets the list (or the count) of courses by session filtered by access_url
3201
     * @param int $session_id The session id
3202
     * @param string $course_name The course code
3203
     * @param string $orderBy Field to order the data
3204
     * @param boolean $getCount Optional. Count the session courses
3205
     * @return array|int List of courses. Whether $getCount is true, return the count
3206
     */
3207
    public static function get_course_list_by_session_id(
3208
        $session_id,
3209
        $course_name = '',
3210
        $orderBy = null,
3211
        $getCount = false
3212
    ) {
3213
        $tbl_course = Database::get_main_table(TABLE_MAIN_COURSE);
3214
        $tbl_session_rel_course = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
3215
3216
        $session_id = intval($session_id);
3217
3218
        $sqlSelect = "SELECT *";
3219
3220
        if ($getCount) {
3221
            $sqlSelect = "SELECT COUNT(1)";
3222
        }
3223
3224
        // select the courses
3225
        $sql = "SELECT *, c.id, c.id as real_id
3226
                FROM $tbl_course c
3227
                INNER JOIN $tbl_session_rel_course src
3228
                ON c.id = src.c_id
3229
		        WHERE src.session_id = '$session_id' ";
3230
3231
        if (!empty($course_name)) {
3232
            $course_name = Database::escape_string($course_name);
3233
            $sql .= " AND c.title LIKE '%$course_name%' ";
3234
        }
3235
3236
        if (!empty($orderBy)) {
3237
            $orderBy = Database::escape_string($orderBy);
3238
            $orderBy = " ORDER BY $orderBy";
3239
        } else {
3240
            if (SessionManager::orderCourseIsEnabled()) {
3241
                $orderBy .= " ORDER BY position ";
3242
            } else {
3243
                $orderBy .= " ORDER BY title ";
3244
            }
3245
        }
3246
3247
        $sql .= Database::escape_string($orderBy);
3248
        $result = Database::query($sql);
3249
        $num_rows = Database::num_rows($result);
3250
        $courses = array();
3251 View Code Duplication
        if ($num_rows > 0) {
3252
            if ($getCount) {
3253
                $count = Database::fetch_array($result);
3254
3255
                return intval($count[0]);
3256
            }
3257
3258
            while ($row = Database::fetch_array($result,'ASSOC'))	{
3259
                $courses[$row['real_id']] = $row;
3260
            }
3261
        }
3262
3263
        return $courses;
3264
    }
3265
3266
    /**
3267
     * Gets the list of courses by session filtered by access_url
3268
     *
3269
     * @param $userId
3270
     * @param $sessionId
3271
     * @param null $from
3272
     * @param null $limit
3273
     * @param null $column
3274
     * @param null $direction
3275
     * @param bool $getCount
3276
     * @return array
3277
     */
3278
    public static function getAllCoursesFollowedByUser(
3279
        $userId,
3280
        $sessionId,
3281
        $from = null,
3282
        $limit = null,
3283
        $column = null,
3284
        $direction = null,
3285
        $getCount = false,
3286
        $keyword = null
3287
    ) {
3288
        if (empty($sessionId)) {
3289
            $sessionsSQL = SessionManager::get_sessions_followed_by_drh(
3290
                $userId,
3291
                null,
3292
                null,
3293
                null,
3294
                true,
3295
                true
3296
            );
3297
        } else {
3298
            $sessionsSQL = intval($sessionId);
3299
        }
3300
3301
        $tbl_course = Database::get_main_table(TABLE_MAIN_COURSE);
3302
        $tbl_session_rel_course	= Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
3303
3304
        if ($getCount) {
3305
            $select = "SELECT COUNT(DISTINCT(c.code)) as count ";
3306
        } else {
3307
            $select = "SELECT DISTINCT c.* ";
3308
        }
3309
3310
        $keywordCondition = null;
3311
        if (!empty($keyword)) {
3312
            $keyword = Database::escape_string($keyword);
3313
            $keywordCondition = " AND (c.code LIKE '%$keyword%' OR c.title LIKE '%$keyword%' ) ";
3314
        }
3315
3316
        // Select the courses
3317
        $sql = "$select
3318
                FROM $tbl_course c
3319
                INNER JOIN $tbl_session_rel_course src
3320
                ON c.id = src.c_id
3321
		        WHERE
3322
		            src.session_id IN ($sessionsSQL)
3323
		            $keywordCondition
3324
		        ";
3325
        if ($getCount) {
3326
            $result = Database::query($sql);
3327
            $row = Database::fetch_array($result,'ASSOC');
3328
            return $row['count'];
3329
        }
3330
3331 View Code Duplication
        if (isset($from) && isset($limit)) {
3332
            $from = intval($from);
3333
            $limit = intval($limit);
3334
            $sql .= " LIMIT $from, $limit";
3335
        }
3336
3337
        $result = Database::query($sql);
3338
        $num_rows = Database::num_rows($result);
3339
        $courses = array();
3340
3341
        if ($num_rows > 0) {
3342
            while ($row = Database::fetch_array($result,'ASSOC'))	{
3343
                $courses[$row['id']] = $row;
3344
            }
3345
        }
3346
3347
        return $courses;
3348
    }
3349
3350
    /**
3351
     * Gets the list of courses by session filtered by access_url
3352
     * @param int $session_id
3353
     * @param string $course_name
3354
     * @return array list of courses
3355
     */
3356
    public static function get_course_list_by_session_id_like($session_id, $course_name = '')
3357
    {
3358
        $tbl_course = Database::get_main_table(TABLE_MAIN_COURSE);
3359
        $tbl_session_rel_course = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
3360
3361
        $session_id = intval($session_id);
3362
        $course_name = Database::escape_string($course_name);
3363
3364
        // select the courses
3365
        $sql = "SELECT c.id, c.title FROM $tbl_course c
3366
                INNER JOIN $tbl_session_rel_course src
3367
                ON c.id = src.c_id
3368
		        WHERE ";
3369
3370
        if (!empty($session_id)) {
3371
            $sql .= "src.session_id LIKE '$session_id' AND ";
3372
        }
3373
3374
        if (!empty($course_name)) {
3375
            $sql .= "UPPER(c.title) LIKE UPPER('%$course_name%') ";
3376
        }
3377
3378
        $sql .= "ORDER BY title;";
3379
        $result = Database::query($sql);
3380
        $num_rows = Database::num_rows($result);
3381
        $courses = array();
3382
        if ($num_rows > 0) {
3383
            while ($row = Database::fetch_array($result, 'ASSOC')) {
3384
                $courses[$row['id']] = $row;
3385
            }
3386
        }
3387
3388
        return $courses;
3389
    }
3390
3391
3392
    /**
3393
     * Gets the count of courses by session filtered by access_url
3394
     * @param int session id
3395
     * @return array list of courses
3396
     */
3397
    public static function getCourseCountBySessionId($session_id, $keyword = null)
3398
    {
3399
        $tbl_course = Database::get_main_table(TABLE_MAIN_COURSE);
3400
        $tbl_session_rel_course = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
3401
        $session_id = intval($session_id);
3402
3403
        // select the courses
3404
        $sql = "SELECT COUNT(c.code) count
3405
                FROM $tbl_course c
3406
                INNER JOIN $tbl_session_rel_course src
3407
                ON c.id = src.c_id
3408
		        WHERE src.session_id = '$session_id' ";
3409
3410
        $keywordCondition = null;
3411
        if (!empty($keyword)) {
3412
            $keyword = Database::escape_string($keyword);
3413
            $keywordCondition = " AND (c.code LIKE '%$keyword%' OR c.title LIKE '%$keyword%' ) ";
3414
        }
3415
        $sql .= $keywordCondition;
3416
3417
        $result = Database::query($sql);
3418
        $num_rows = Database::num_rows($result);
3419
        if ($num_rows > 0) {
3420
            $row = Database::fetch_array($result,'ASSOC');
3421
            return $row['count'];
3422
        }
3423
3424
        return null;
3425
    }
3426
3427
    /**
3428
     * Get the session id based on the original id and field name in the extra fields.
3429
     * Returns 0 if session was not found
3430
     *
3431
     * @param string $value Original session id
3432
     * @param string $variable Original field name
3433
     * @return int Session id
3434
     */
3435
    public static function getSessionIdFromOriginalId($value, $variable)
3436
    {
3437
        $extraFieldValue = new ExtraFieldValue('session');
3438
        $result = $extraFieldValue->get_item_id_from_field_variable_and_field_value(
3439
            $variable,
3440
            $value
3441
        );
3442
3443
        if (!empty($result)) {
3444
            return $result['item_id'];
3445
        }
3446
3447
        return 0;
3448
    }
3449
3450
    /**
3451
     * Get users by session
3452
     * @param  int $id session id
3453
     * @param	int	$status filter by status coach = 2
3454
     * @return  array a list with an user list
3455
     */
3456
    public static function get_users_by_session($id, $status = null)
3457
    {
3458
        if (empty($id)) {
3459
            return array();
3460
        }
3461
        $id = intval($id);
3462
        $tbl_user = Database::get_main_table(TABLE_MAIN_USER);
3463
        $tbl_session_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_USER);
3464
        $table_access_url_user = Database::get_main_table(TABLE_MAIN_ACCESS_URL_REL_USER);
3465
3466
        $sql = "SELECT
3467
                    u.user_id,
3468
                    lastname,
3469
                    firstname,
3470
                    username,
3471
                    relation_type,
3472
                    access_url_id
3473
                FROM $tbl_user u
3474
                INNER JOIN $tbl_session_rel_user
3475
                ON u.user_id = $tbl_session_rel_user.user_id AND
3476
                $tbl_session_rel_user.session_id = $id
3477
                LEFT OUTER JOIN $table_access_url_user uu
3478
                ON (uu.user_id = u.user_id)
3479
                ";
3480
3481
        $urlId = api_get_current_access_url_id();
3482
        if (isset($status) && $status != '') {
3483
            $status = intval($status);
3484
            $sql .= " WHERE relation_type = $status AND (access_url_id = $urlId OR access_url_id is null )";
3485
        } else {
3486
            $sql .= " WHERE (access_url_id = $urlId OR access_url_id is null )";
3487
        }
3488
3489
        $sql .= " ORDER BY relation_type, ";
3490
        $sql .= api_sort_by_first_name() ? ' firstname, lastname' : '  lastname, firstname';
3491
3492
        $result = Database::query($sql);
3493
3494
        $return = array();
3495
        while ($row = Database::fetch_array($result, 'ASSOC')) {
3496
            $return[] = $row;
3497
        }
3498
3499
        return $return;
3500
    }
3501
3502
    /**
3503
     * The general coach (field: session.id_coach)
3504
     * @param int $user_id user id
3505
     * @param boolean   $asPlatformAdmin The user is platform admin, return everything
3506
     * @return array
3507
     */
3508
    public static function get_sessions_by_general_coach($user_id, $asPlatformAdmin = false)
3509
    {
3510
        $session_table = Database::get_main_table(TABLE_MAIN_SESSION);
3511
        $user_id = intval($user_id);
3512
3513
        // Session where we are general coach
3514
        $sql = "SELECT DISTINCT *
3515
                FROM $session_table";
3516
3517
        if (!$asPlatformAdmin) {
3518
            $sql .= " WHERE id_coach = $user_id";
3519
        }
3520
3521
        if (api_is_multiple_url_enabled()) {
3522
            $tbl_session_rel_access_url = Database::get_main_table(TABLE_MAIN_ACCESS_URL_REL_SESSION);
3523
            $access_url_id = api_get_current_access_url_id();
3524
3525
            $sqlCoach = '';
3526
            if (!$asPlatformAdmin) {
3527
                $sqlCoach = " id_coach = $user_id AND ";
3528
            }
3529
3530
            if ($access_url_id != -1) {
3531
                $sql = 'SELECT DISTINCT session.*
3532
                    FROM ' . $session_table . ' session INNER JOIN ' . $tbl_session_rel_access_url . ' session_rel_url
3533
                    ON (session.id = session_rel_url.session_id)
3534
                    WHERE '.$sqlCoach.' access_url_id = ' . $access_url_id;
3535
            }
3536
        }
3537
        $sql .= ' ORDER by name';
3538
        $result = Database::query($sql);
3539
3540
        return Database::store_result($result, 'ASSOC');
3541
    }
3542
3543
    /**
3544
     * @param int $user_id
3545
     * @return array
3546
     * @deprecated use get_sessions_by_general_coach()
3547
     */
3548
    public static function get_sessions_by_coach($user_id)
3549
    {
3550
        $session_table = Database::get_main_table(TABLE_MAIN_SESSION);
3551
        return Database::select('*', $session_table, array('where' => array('id_coach = ?' => $user_id)));
3552
    }
3553
3554
    /**
3555
     * @param int $user_id
3556
     * @param int $courseId
3557
     * @param int $session_id
3558
     * @return array|bool
3559
     */
3560 View Code Duplication
    public static function get_user_status_in_course_session($user_id, $courseId, $session_id)
3561
    {
3562
        $tbl_session_rel_course_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
3563
        $tbl_user = Database::get_main_table(TABLE_MAIN_USER);
3564
        $sql = "SELECT session_rcru.status
3565
                FROM $tbl_session_rel_course_rel_user session_rcru, $tbl_user user
3566
                WHERE
3567
                    session_rcru.user_id = user.user_id AND
3568
                    session_rcru.session_id = '" . intval($session_id) . "' AND
3569
                    session_rcru.c_id ='" . intval($courseId) . "' AND
3570
                    user.user_id = " . intval($user_id);
3571
3572
        $result = Database::query($sql);
3573
        $status = false;
3574
        if (Database::num_rows($result)) {
3575
            $status = Database::fetch_row($result);
3576
            $status = $status['0'];
3577
        }
3578
3579
        return $status;
3580
    }
3581
3582
    /**
3583
     * Gets user status within a session
3584
     * @param int $user_id
3585
     * @param int $courseId
3586
     * @param $session_id
3587
     * @return int
3588
     * @assert (null,null,null) === false
3589
     */
3590
    public static function get_user_status_in_session($user_id, $courseId, $session_id)
3591
    {
3592
        if (empty($user_id) or empty($courseId) or empty($session_id)) {
3593
            return false;
3594
        }
3595
        $tbl_session_rel_course_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
3596
        $tbl_user = Database::get_main_table(TABLE_MAIN_USER);
3597
        $sql = "SELECT session_rcru.status
3598
                FROM $tbl_session_rel_course_rel_user session_rcru, $tbl_user user
3599
                WHERE session_rcru.user_id = user.user_id AND
3600
                    session_rcru.session_id = '" . intval($session_id) . "' AND
3601
                    session_rcru.c_id ='" . intval($courseId) . "' AND
3602
                    user.user_id = " . intval($user_id);
3603
        $result = Database::query($sql);
3604
        $status = false;
3605
        if (Database::num_rows($result)) {
3606
            $status = Database::fetch_row($result);
3607
            $status = $status['0'];
3608
        }
3609
        return $status;
3610
    }
3611
3612
    /**
3613
     * @param int $id
3614
     * @return array
3615
     */
3616
    public static function get_all_sessions_by_promotion($id)
3617
    {
3618
        $t = Database::get_main_table(TABLE_MAIN_SESSION);
3619
        return Database::select('*', $t, array('where' => array('promotion_id = ?' => $id)));
3620
    }
3621
3622
    /**
3623
     * @param int $promotion_id
3624
     * @param array $list
3625
     */
3626
    public static function suscribe_sessions_to_promotion($promotion_id, $list)
3627
    {
3628
        $t = Database::get_main_table(TABLE_MAIN_SESSION);
3629
        $params = array();
3630
        $params['promotion_id'] = 0;
3631
        Database::update($t, $params, array('promotion_id = ?' => $promotion_id));
3632
3633
        $params['promotion_id'] = $promotion_id;
3634
        if (!empty($list)) {
3635
            foreach ($list as $session_id) {
3636
                $session_id = intval($session_id);
3637
                Database::update($t, $params, array('id = ?' => $session_id));
3638
            }
3639
        }
3640
    }
3641
3642
    /**
3643
     * Updates a session status
3644
     * @param	int 	session id
3645
     * @param	int 	status
3646
     */
3647
    public static function set_session_status($session_id, $status)
3648
    {
3649
        $t = Database::get_main_table(TABLE_MAIN_SESSION);
3650
        $params['visibility'] = $status;
3651
        Database::update($t, $params, array('id = ?' => $session_id));
3652
    }
3653
3654
    /**
3655
     * Copies a session with the same data to a new session.
3656
     * The new copy is not assigned to the same promotion. @see suscribe_sessions_to_promotions() for that
3657
     * @param   int     Session ID
3658
     * @param   bool    Whether to copy the relationship with courses
3659
     * @param   bool    Whether to copy the relationship with users
3660
     * @param   bool    New courses will be created
3661
     * @param   bool    Whether to set exercises and learning paths in the new session to invisible by default
3662
     * @return  int     The new session ID on success, 0 otherwise
3663
     * @todo make sure the extra session fields are copied too
3664
     */
3665
    public static function copy(
3666
        $id,
3667
        $copy_courses = true,
3668
        $copy_users = true,
3669
        $create_new_courses = false,
3670
        $set_exercises_lp_invisible = false
3671
    ) {
3672
        $id = intval($id);
3673
        $s = self::fetch($id);
3674
        // Check all dates before copying
3675
        // Get timestamp for now in UTC - see http://php.net/manual/es/function.time.php#117251
3676
        $now = time() - date('Z');
3677
        // Timestamp in one month
3678
        $inOneMonth = $now + (30*24*3600);
3679
        $inOneMonth = api_get_local_time($inOneMonth);
3680
        if (api_strtotime($s['access_start_date']) < $now) {
3681
            $s['access_start_date'] = api_get_local_time($now);
3682
        }
3683
        if (api_strtotime($s['display_start_date']) < $now) {
3684
            $s['display_start_date'] = api_get_local_time($now);
3685
        }
3686
        if (api_strtotime($s['coach_access_start_date']) < $now) {
3687
            $s['coach_access_start_date'] = api_get_local_time($now);
3688
        }
3689
        if (api_strtotime($s['access_end_date']) < $now) {
3690
            $s['access_end_date'] = $inOneMonth;
3691
        }
3692
        if (api_strtotime($s['display_end_date']) < $now) {
3693
            $s['display_end_date'] = $inOneMonth;
3694
        }
3695
        if (api_strtotime($s['coach_access_end_date']) < $now) {
3696
            $s['coach_access_end_date'] = $inOneMonth;
3697
        }
3698
        // Now try to create the session
3699
        $sid = self::create_session(
3700
            $s['name'] . ' ' . get_lang('CopyLabelSuffix'),
3701
            $s['access_start_date'],
3702
            $s['access_end_date'],
3703
            $s['display_start_date'],
3704
            $s['display_end_date'],
3705
            $s['coach_access_start_date'],
3706
            $s['coach_access_end_date'],
3707
            (int)$s['id_coach'],
3708
            $s['session_category_id'],
3709
            (int)$s['visibility'],
3710
            true
3711
        );
3712
3713
        if (!is_numeric($sid) || empty($sid)) {
3714
            return false;
3715
        }
3716
3717
        if ($copy_courses) {
3718
            // Register courses from the original session to the new session
3719
            $courses = self::get_course_list_by_session_id($id);
3720
3721
            $short_courses = $new_short_courses = array();
3722
            if (is_array($courses) && count($courses) > 0) {
3723
                foreach ($courses as $course) {
3724
                    $short_courses[] = $course;
3725
                }
3726
            }
3727
3728
            $courses = null;
3729
3730
            //We will copy the current courses of the session to new courses
3731
            if (!empty($short_courses)) {
3732
                if ($create_new_courses) {
3733
                    //Just in case
3734
                    if (function_exists('ini_set')) {
3735
                        api_set_memory_limit('256M');
3736
                        ini_set('max_execution_time', 0);
3737
                    }
3738
                    $params = array();
3739
                    $params['skip_lp_dates'] = true;
3740
3741
                    foreach ($short_courses as $course_data) {
3742
                        $course_info = CourseManager::copy_course_simple(
3743
                            $course_data['title'].' '.get_lang(
3744
                                'CopyLabelSuffix'
3745
                            ),
3746
                            $course_data['course_code'],
3747
                            $id,
3748
                            $sid,
3749
                            $params
3750
                        );
3751
3752
                        if ($course_info) {
3753
                            //By default new elements are invisible
3754
                            if ($set_exercises_lp_invisible) {
3755
                                $list = new LearnpathList('', $course_info['code'], $sid);
3756
                                $flat_list = $list->get_flat_list();
3757
                                if (!empty($flat_list)) {
3758
                                    foreach ($flat_list as $lp_id => $data) {
3759
                                        api_item_property_update(
3760
                                            $course_info,
0 ignored issues
show
Bug introduced by
It seems like $course_info defined by \CourseManager::copy_cou...'], $id, $sid, $params) on line 3742 can also be of type boolean; however, api_item_property_update() does only seem to accept array, maybe add an additional type check?

If a method or function can return multiple different values and unless you are sure that you only can receive a single value in this context, we recommend to add an additional type check:

/**
 * @return array|string
 */
function returnsDifferentValues($x) {
    if ($x) {
        return 'foo';
    }

    return array();
}

$x = returnsDifferentValues($y);
if (is_array($x)) {
    // $x is an array.
}

If this a common case that PHP Analyzer should handle natively, please let us know by opening an issue.

Loading history...
3761
                                            TOOL_LEARNPATH,
3762
                                            $lp_id,
3763
                                            'invisible',
3764
                                            api_get_user_id(),
3765
                                            0,
3766
                                            0,
3767
                                            0,
3768
                                            0,
3769
                                            $sid
3770
                                        );
3771
                                    }
3772
                                }
3773
                                $quiz_table = Database::get_course_table(TABLE_QUIZ_TEST);
3774
                                $course_id = $course_info['real_id'];
3775
                                //@todo check this query
3776
                                $sql = "UPDATE $quiz_table SET active = 0
3777
                                        WHERE c_id = $course_id AND session_id = $sid";
3778
                                Database::query($sql);
3779
                            }
3780
                            $new_short_courses[] = $course_info['real_id'];
3781
                        }
3782
                    }
3783
                } else {
3784
                    foreach ($short_courses as $course_data) {
3785
                        $new_short_courses[] = $course_data['id'];
3786
                    }
3787
                }
3788
3789
                $short_courses = $new_short_courses;
3790
                self::add_courses_to_session($sid, $short_courses, true);
3791
                $short_courses = null;
3792
            }
3793
        }
3794
        if ($copy_users) {
3795
            // Register users from the original session to the new session
3796
            $users = self::get_users_by_session($id);
3797
            $short_users = array();
3798
            if (is_array($users) && count($users) > 0) {
3799
                foreach ($users as $user) {
3800
                    $short_users[] = $user['user_id'];
3801
                }
3802
            }
3803
            $users = null;
3804
            //Subscribing in read only mode
3805
            self::suscribe_users_to_session($sid, $short_users, SESSION_VISIBLE_READ_ONLY, true);
3806
            $short_users = null;
3807
        }
3808
        return $sid;
3809
    }
3810
3811
    /**
3812
     * @param int $user_id
3813
     * @param int $session_id
3814
     * @return bool
3815
     */
3816
    static function user_is_general_coach($user_id, $session_id)
3817
    {
3818
        $session_id = intval($session_id);
3819
        $user_id = intval($user_id);
3820
        $session_table = Database::get_main_table(TABLE_MAIN_SESSION);
3821
        $sql = "SELECT DISTINCT id
3822
	         	FROM $session_table
3823
	         	WHERE session.id_coach =  '" . $user_id . "' AND id = '$session_id'";
3824
        $result = Database::query($sql);
3825
        if ($result && Database::num_rows($result)) {
3826
            return true;
3827
        }
3828
        return false;
3829
    }
3830
3831
    /**
3832
     * Get the number of sessions
3833
     * @param  int ID of the URL we want to filter on (optional)
3834
     * @return int Number of sessions
3835
     */
3836
    public static function count_sessions($access_url_id = null)
3837
    {
3838
        $session_table = Database::get_main_table(TABLE_MAIN_SESSION);
3839
        $access_url_rel_session_table = Database::get_main_table(TABLE_MAIN_ACCESS_URL_REL_SESSION);
3840
        $sql = "SELECT count(id) FROM $session_table s";
3841
        if (!empty($access_url_id) && $access_url_id == intval($access_url_id)) {
3842
            $sql .= ", $access_url_rel_session_table u " .
3843
                " WHERE s.id = u.session_id AND u.access_url_id = $access_url_id";
3844
        }
3845
        $res = Database::query($sql);
3846
        $row = Database::fetch_row($res);
3847
        return $row[0];
3848
    }
3849
3850
    /**
3851
     * Protect a session to be edited.
3852
     * @param int $id
3853
     * @param bool $checkSession
3854
     */
3855
    public static function protectSession($id, $checkSession = true)
3856
    {
3857
        // api_protect_admin_script(true);
3858
        if (self::allowToManageSessions()) {
3859
3860
            if (api_is_platform_admin()) {
3861
                return true;
3862
            }
3863
3864
            if ($checkSession) {
3865
                if (self::allowed($id)) {
3866
                    return true;
3867
                } else {
3868
                    api_not_allowed(true);
3869
                }
3870
            }
3871
        } else {
3872
            api_not_allowed(true);
3873
        }
3874
    }
3875
3876
    /**
3877
     * @param int $id
3878
     * @return bool
3879
     */
3880
    private static function allowed($id)
3881
    {
3882
        $sessionInfo = self::fetch($id);
3883
3884
        if (empty($sessionInfo)) {
3885
            return false;
3886
        }
3887
3888
        if (api_is_platform_admin()) {
3889
            return true;
3890
        }
3891
3892
        $userId = api_get_user_id();
3893
3894
        if (api_is_session_admin() &&
3895
            api_get_setting('allow_session_admins_to_manage_all_sessions') != 'true'
3896
        ) {
3897
            if ($sessionInfo['session_admin_id'] != $userId) {
3898
                return false;
3899
            }
3900
        }
3901
3902
        if (api_is_teacher() &&
3903
            api_get_setting('allow_teachers_to_create_sessions') == 'true'
3904
        ) {
3905
            if ($sessionInfo['id_coach'] != $userId) {
3906
                return false;
3907
            }
3908
        }
3909
3910
        return true;
3911
    }
3912
3913
    /**
3914
     * @return bool
3915
     */
3916
    public static function allowToManageSessions()
3917
    {
3918
        if (self::allowManageAllSessions()) {
3919
            return true;
3920
        }
3921
3922
        $setting = api_get_setting('allow_teachers_to_create_sessions');
3923
3924
        if (api_is_teacher() && $setting == 'true') {
3925
3926
            return true;
3927
        }
3928
3929
        return false;
3930
    }
3931
3932
    /**
3933
     * @return bool
3934
     */
3935
    public static function allowOnlyMySessions()
3936
    {
3937
        if (self::allowToManageSessions() &&
3938
            !api_is_platform_admin() &&
3939
            api_is_teacher()
3940
        ) {
3941
            return true;
3942
        }
3943
3944
        return false;
3945
    }
3946
3947
    /**
3948
     * @return bool
3949
     */
3950
    public static function allowManageAllSessions()
3951
    {
3952
        if (api_is_platform_admin()) {
3953
            return true;
3954
        }
3955
3956
        return false;
3957
    }
3958
3959
    /**
3960
     * @param $id
3961
     * @return bool
3962
     */
3963
    public static function protect_teacher_session_edit($id)
3964
    {
3965
        if (!api_is_coach($id) && !api_is_platform_admin()) {
3966
            api_not_allowed(true);
3967
        } else {
3968
            return true;
3969
        }
3970
    }
3971
3972
    /**
3973
     * @param int $courseId
3974
     * @return array
3975
     */
3976
    public static function get_session_by_course($courseId)
3977
    {
3978
        $table_session_course = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
3979
        $table_session = Database::get_main_table(TABLE_MAIN_SESSION);
3980
        $courseId = intval($courseId);
3981
        $sql = "SELECT name, s.id
3982
                FROM $table_session_course sc
3983
                INNER JOIN $table_session s ON (sc.session_id = s.id)
3984
                WHERE sc.c_id = '$courseId' ";
3985
        $result = Database::query($sql);
3986
3987
        return Database::store_result($result);
3988
    }
3989
3990
    /**
3991
     * @param int $user_id
3992
     * @param bool $ignore_visibility_for_admins
3993
     * @param bool $ignoreTimeLimit
3994
     *
3995
     * @return array
3996
     */
3997
    public static function get_sessions_by_user($user_id, $ignore_visibility_for_admins = false, $ignoreTimeLimit = false)
3998
    {
3999
        $sessionCategories = UserManager::get_sessions_by_category(
4000
            $user_id,
4001
            false,
4002
            $ignore_visibility_for_admins,
4003
            $ignoreTimeLimit
4004
        );
4005
        $sessionArray = array();
4006
        if (!empty($sessionCategories)) {
4007
            foreach ($sessionCategories as $category) {
4008
                if (isset($category['sessions'])) {
4009
                    foreach ($category['sessions'] as $session) {
4010
                        $sessionArray[] = $session;
4011
                    }
4012
                }
4013
            }
4014
        }
4015
4016
        return $sessionArray;
4017
    }
4018
4019
    /**
4020
     * @param string $file
4021
     * @param bool $updateSession options:
4022
     *  true: if the session exists it will be updated.
4023
     *  false: if session exists a new session will be created adding a counter session1, session2, etc
4024
     * @param int $defaultUserId
4025
     * @param mixed $logger
4026
     * @param array $extraFields convert a file row to an extra field. Example in CSV file there's a SessionID then it will
4027
     * converted to extra_external_session_id if you set this: array('SessionId' => 'extra_external_session_id')
4028
     * @param string $extraFieldId
4029
     * @param int $daysCoachAccessBeforeBeginning
4030
     * @param int $daysCoachAccessAfterBeginning
4031
     * @param int $sessionVisibility
4032
     * @param array $fieldsToAvoidUpdate
4033
     * @param bool $deleteUsersNotInList
4034
     * @param bool $updateCourseCoaches
4035
     * @param bool $sessionWithCoursesModifier
4036
     * @param int $showDescription
4037
     * @param array $teacherBackupList
4038
     * @param array $groupBackup
4039
     * @return array
4040
     */
4041
    static function importCSV(
4042
        $file,
4043
        $updateSession,
4044
        $defaultUserId = null,
4045
        $logger = null,
4046
        $extraFields = array(),
4047
        $extraFieldId = null,
4048
        $daysCoachAccessBeforeBeginning = null,
4049
        $daysCoachAccessAfterBeginning = null,
4050
        $sessionVisibility = 1,
4051
        $fieldsToAvoidUpdate = array(),
4052
        $deleteUsersNotInList = false,
4053
        $updateCourseCoaches = false,
4054
        $sessionWithCoursesModifier = false,
4055
        $addOriginalCourseTeachersAsCourseSessionCoaches = true,
4056
        $removeAllTeachersFromCourse = true,
4057
        $showDescription = null,
4058
        &$teacherBackupList = array(),
4059
        &$groupBackup = array()
4060
    ) {
4061
        $content = file($file);
4062
4063
        $error_message = null;
4064
        $session_counter = 0;
4065
4066
        if (empty($defaultUserId)) {
4067
            $defaultUserId = api_get_user_id();
4068
        }
4069
4070
        $eol = PHP_EOL;
4071
        if (PHP_SAPI != 'cli') {
4072
            $eol = '<br />';
4073
        }
4074
4075
        $debug = false;
4076
        if (isset($logger)) {
4077
            $debug = true;
4078
        }
4079
4080
        $extraParameters = null;
4081
4082
        if (!empty($daysCoachAccessBeforeBeginning) && !empty($daysCoachAccessAfterBeginning)) {
4083
            $extraParameters .= ' , nb_days_access_before_beginning = '.intval($daysCoachAccessBeforeBeginning);
4084
            $extraParameters .= ' , nb_days_access_after_end = '.intval($daysCoachAccessAfterBeginning);
4085
        }
4086
4087
        if (!is_null($showDescription)) {
4088
            $extraParameters .= ' , show_description = '.intval($showDescription);
4089
        }
4090
4091
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
4092
        $tbl_session_user = Database::get_main_table(TABLE_MAIN_SESSION_USER);
4093
        $tbl_session_course  = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
4094
        $tbl_session_course_user = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
4095
4096
        $sessions = array();
4097
4098
        if (!api_strstr($content[0], ';')) {
4099
            $error_message = get_lang('NotCSV');
4100
        } else {
4101
            $tag_names = array();
4102
4103 View Code Duplication
            foreach ($content as $key => $enreg) {
4104
                $enreg = explode(';', trim($enreg));
4105
                if ($key) {
4106
                    foreach ($tag_names as $tag_key => $tag_name) {
4107
                        $sessions[$key - 1][$tag_name] = $enreg[$tag_key];
4108
                    }
4109
                } else {
4110
                    foreach ($enreg as $tag_name) {
4111
                        $tag_names[] = api_preg_replace('/[^a-zA-Z0-9_\-]/', '', $tag_name);
4112
                    }
4113
                    if (!in_array('SessionName', $tag_names) ||
4114
                        !in_array('DateStart', $tag_names) ||
4115
                        !in_array('DateEnd', $tag_names)
4116
                    ) {
4117
                        $error_message = get_lang('NoNeededData');
4118
                        break;
4119
                    }
4120
                }
4121
            }
4122
4123
            $sessionList = array();
4124
            // Looping the sessions.
4125
            foreach ($sessions as $enreg) {
4126
                $user_counter = 0;
4127
                $course_counter = 0;
4128
4129
                if (isset($extraFields) && !empty($extraFields)) {
4130
                    foreach ($extraFields as $original => $to) {
4131
                        $enreg[$to] = isset($enreg[$original]) ? $enreg[$original] : null;
4132
                    }
4133
                }
4134
4135
                $session_name = Database::escape_string($enreg['SessionName']);
4136
                // Default visibility
4137
                $visibilityAfterExpirationPerSession = $sessionVisibility;
4138
4139
                if (isset($enreg['VisibilityAfterExpiration'])) {
4140
                    $visibility = $enreg['VisibilityAfterExpiration'];
4141
                    switch ($visibility) {
4142
                        case 'read_only':
4143
                            $visibilityAfterExpirationPerSession = SESSION_VISIBLE_READ_ONLY;
4144
                            break;
4145
                        case 'accessible':
4146
                            $visibilityAfterExpirationPerSession = SESSION_VISIBLE;
4147
                            break;
4148
                        case 'not_accessible':
4149
                            $visibilityAfterExpirationPerSession = SESSION_INVISIBLE;
4150
                            break;
4151
                    }
4152
                }
4153
4154
                if (empty($session_name)) {
4155
                    continue;
4156
                }
4157
4158
                $date_start = $enreg['DateStart'];
4159
                $date_end = $enreg['DateEnd'];
4160
                $session_category_id = isset($enreg['SessionCategory']) ? $enreg['SessionCategory'] : null;
4161
                $sessionDescription = isset($enreg['SessionDescription']) ? $enreg['SessionDescription'] : null;
4162
4163
                $extraSessionParameters = null;
4164
                if (!empty($sessionDescription)) {
4165
                    $extraSessionParameters = " , description = '".Database::escape_string($sessionDescription)."'";
4166
                }
4167
4168
                // Searching a general coach.
4169
                if (!empty($enreg['Coach'])) {
4170
                    $coach_id = UserManager::get_user_id_from_username($enreg['Coach']);
4171
                    if ($coach_id === false) {
4172
                        // If the coach-user does not exist - I'm the coach.
4173
                        $coach_id = $defaultUserId;
4174
                    }
4175
                } else {
4176
                    $coach_id = $defaultUserId;
4177
                }
4178
4179
                if (!$updateSession) {
4180
                    // Always create a session.
4181
                    $unique_name = false;
4182
                    $i = 0;
4183
                    // Change session name, verify that session doesn't exist.
4184
                    $suffix = null;
4185 View Code Duplication
                    while (!$unique_name) {
4186
                        if ($i > 1) {
4187
                            $suffix = ' - ' . $i;
4188
                        }
4189
                        $sql = 'SELECT 1 FROM ' . $tbl_session . '
4190
                                WHERE name="' . $session_name . $suffix . '"';
4191
                        $rs = Database::query($sql);
4192
4193
                        if (Database::result($rs, 0, 0)) {
4194
                            $i++;
4195
                        } else {
4196
                            $unique_name = true;
4197
                            $session_name .= $suffix;
4198
                        }
4199
                    }
4200
4201
                    $sessionCondition = '';
4202
                    if (!empty($session_category_id)) {
4203
                        $sessionCondition = "session_category_id = '$session_category_id',";
4204
                    }
4205
4206
                    // Creating the session.
4207
                    $sql = "INSERT IGNORE INTO $tbl_session SET
4208
                            name = '" . $session_name . "',
4209
                            id_coach = '$coach_id',
4210
                            access_start_date = '$date_start',
4211
                            access_end_date = '$date_end',
4212
                            visibility = '$visibilityAfterExpirationPerSession',
4213
                            $sessionCondition
4214
                            session_admin_id = " . intval($defaultUserId) . $extraParameters . $extraSessionParameters;
4215
                    Database::query($sql);
4216
4217
                    $session_id = Database::insert_id();
4218
                    if ($debug) {
4219
                        if ($session_id) {
4220 View Code Duplication
                            foreach ($enreg as $key => $value) {
4221
                                if (substr($key, 0, 6) == 'extra_') { //an extra field
4222
                                    self::update_session_extra_field_value($session_id, substr($key, 6), $value);
4223
                                }
4224
                            }
4225
4226
                            $logger->addInfo("Sessions - Session created: #$session_id - $session_name");
4227
                        } else {
4228
                            $logger->addError("Sessions - Session NOT created: $session_name");
4229
                        }
4230
                    }
4231
                    $session_counter++;
4232
                } else {
4233
                    $sessionId = null;
4234
                    if (isset($extraFields) && !empty($extraFields) && !empty($enreg['extra_'.$extraFieldId])) {
4235
                        $sessionId = self::getSessionIdFromOriginalId($enreg['extra_'.$extraFieldId], $extraFieldId);
4236
                        if (empty($sessionId)) {
4237
                            $my_session_result = false;
4238
                        } else {
4239
                            $my_session_result = true;
4240
                        }
4241
                    } else {
4242
                        $my_session_result = self::get_session_by_name($enreg['SessionName']);
4243
                    }
4244
4245
                    if ($my_session_result === false) {
4246
4247
                        // Creating a session.
4248
                        $sql = "INSERT IGNORE INTO $tbl_session SET
4249
                                name = '$session_name',
4250
                                id_coach = '$coach_id',
4251
                                access_start_date = '$date_start',
4252
                                access_end_date = '$date_end',
4253
                                visibility = '$visibilityAfterExpirationPerSession',
4254
                                session_category_id = '$session_category_id' " . $extraParameters . $extraSessionParameters;
4255
4256
                        Database::query($sql);
4257
4258
                        // We get the last insert id.
4259
                        $my_session_result = SessionManager::get_session_by_name($enreg['SessionName']);
4260
                        $session_id = $my_session_result['id'];
4261
4262
                        if ($session_id) {
4263 View Code Duplication
                            foreach ($enreg as $key => $value) {
4264
                                if (substr($key, 0, 6) == 'extra_') { //an extra field
4265
                                    self::update_session_extra_field_value($session_id, substr($key, 6), $value);
4266
                                }
4267
                            }
4268
                            if ($debug) {
4269
                                $logger->addInfo("Sessions - #$session_id created: $session_name");
4270
                            }
4271
4272
                            // Delete session-user relation only for students
4273
                            $sql = "DELETE FROM $tbl_session_user
4274
                                    WHERE session_id = '$session_id' AND relation_type <> " . SESSION_RELATION_TYPE_RRHH;
4275
                            Database::query($sql);
4276
4277
                            $sql = "DELETE FROM $tbl_session_course WHERE session_id = '$session_id'";
4278
                            Database::query($sql);
4279
4280
                            // Delete session-course-user relationships students and coaches.
4281 View Code Duplication
                            if ($updateCourseCoaches) {
4282
                                $sql = "DELETE FROM $tbl_session_course_user
4283
                                        WHERE session_id = '$session_id' AND status in ('0', '2')";
4284
                                Database::query($sql);
4285
                            } else {
4286
                                // Delete session-course-user relation ships *only* for students.
4287
                                $sql = "DELETE FROM $tbl_session_course_user
4288
                                        WHERE session_id = '$session_id' AND status <> 2";
4289
                                Database::query($sql);
4290
                            }
4291
                        }
4292
                    } else {
4293
                        if ($debug) {
4294
                            $logger->addError("Sessions - Session to be updated: $session_name");
4295
                        }
4296
4297
                        // Updating the session.
4298
                        $params = array(
4299
                            'id_coach' => $coach_id,
4300
                            'access_start_date' => $date_start,
4301
                            'access_end_date' => $date_end,
4302
                            'visibility' => $visibilityAfterExpirationPerSession,
4303
                            'session_category_id' => $session_category_id,
4304
                        );
4305
4306
                        if (!empty($sessionDescription)) {
4307
                            $params['description'] = $sessionDescription;
4308
                        }
4309
4310
                        if (!empty($fieldsToAvoidUpdate)) {
4311
                            foreach ($fieldsToAvoidUpdate as $field) {
4312
                                unset($params[$field]);
4313
                            }
4314
                        }
4315
4316 View Code Duplication
                        if (isset($sessionId) && !empty($sessionId)) {
4317
                            if (!empty($enreg['SessionName'])) {
4318
                                $params['name'] = $enreg['SessionName'];
4319
                            }
4320
                            $session_id = $sessionId;
4321
                        } else {
4322
                            $row = Database::query("SELECT id FROM $tbl_session WHERE name = '$session_name'");
4323
                            list($session_id) = Database::fetch_array($row);
0 ignored issues
show
Bug introduced by
It seems like $row can be null; however, fetch_array() does not accept null, maybe add an additional type check?

Unless you are absolutely sure that the expression can never be null because of other conditions, we strongly recommend to add an additional type check to your code:

/** @return stdClass|null */
function mayReturnNull() { }

function doesNotAcceptNull(stdClass $x) { }

// With potential error.
function withoutCheck() {
    $x = mayReturnNull();
    doesNotAcceptNull($x); // Potential error here.
}

// Safe - Alternative 1
function withCheck1() {
    $x = mayReturnNull();
    if ( ! $x instanceof stdClass) {
        throw new \LogicException('$x must be defined.');
    }
    doesNotAcceptNull($x);
}

// Safe - Alternative 2
function withCheck2() {
    $x = mayReturnNull();
    if ($x instanceof stdClass) {
        doesNotAcceptNull($x);
    }
}
Loading history...
4324
                        }
4325
4326
                        if ($session_id) {
4327
4328
                            if ($debug) {
4329
                                $logger->addError("Sessions - Session to be updated #$session_id");
4330
                            }
4331
4332
                            $sessionInfo = api_get_session_info($session_id);
4333
4334
                            $params['show_description'] = isset($sessionInfo['show_description']) ? $sessionInfo['show_description'] : intval($showDescription);
4335
4336
                            if (!empty($daysCoachAccessBeforeBeginning) && !empty($daysCoachAccessAfterBeginning)) {
4337 View Code Duplication
                                if (empty($sessionInfo['nb_days_access_before_beginning']) ||
4338
                                    (!empty($sessionInfo['nb_days_access_before_beginning']) &&
4339
                                        $sessionInfo['nb_days_access_before_beginning'] < $daysCoachAccessBeforeBeginning)
4340
                                ) {
4341
                                    $params['nb_days_access_before_beginning'] = intval($daysCoachAccessBeforeBeginning);
4342
                                }
4343
4344 View Code Duplication
                                if (empty($sessionInfo['nb_days_access_after_end']) ||
4345
                                    (!empty($sessionInfo['nb_days_access_after_end']) &&
4346
                                        $sessionInfo['nb_days_access_after_end'] < $daysCoachAccessAfterBeginning)
4347
                                ) {
4348
                                    $params['nb_days_access_after_end'] = intval($daysCoachAccessAfterBeginning);
4349
                                }
4350
                            }
4351
4352
                            Database::update($tbl_session, $params, array('id = ?' => $session_id));
4353
4354 View Code Duplication
                            foreach ($enreg as $key => $value) {
4355
                                if (substr($key, 0, 6) == 'extra_') { //an extra field
4356
                                    self::update_session_extra_field_value($session_id, substr($key, 6), $value);
4357
                                }
4358
                            }
4359
4360
                            // Delete session-user relation only for students
4361
                            $sql = "DELETE FROM $tbl_session_user
4362
                                    WHERE session_id = '$session_id' AND relation_type <> " . SESSION_RELATION_TYPE_RRHH;
4363
                            Database::query($sql);
4364
4365
                            $sql = "DELETE FROM $tbl_session_course WHERE session_id = '$session_id'";
4366
                            Database::query($sql);
4367
4368
                            // Delete session-course-user relationships students and coaches.
4369 View Code Duplication
                            if ($updateCourseCoaches) {
4370
                                $sql = "DELETE FROM $tbl_session_course_user
4371
                                        WHERE session_id = '$session_id' AND status in ('0', '2')";
4372
                                Database::query($sql);
4373
                            } else {
4374
                                // Delete session-course-user relation ships *only* for students.
4375
                                $sql = "DELETE FROM $tbl_session_course_user
4376
                                        WHERE session_id = '$session_id' AND status <> 2";
4377
                                Database::query($sql);
4378
                            }
4379
                        } else {
4380
                            if ($debug) {
4381
                                $logger->addError(
4382
                                    "Sessions - Session not found"
4383
                                );
4384
                            }
4385
                        }
4386
                    }
4387
                    $session_counter++;
4388
                }
4389
4390
                $sessionList[] = $session_id;
4391
                $users = explode('|', $enreg['Users']);
4392
4393
                // Adding the relationship "Session - User" for students
4394
                $userList = array();
4395
4396
                if (is_array($users)) {
4397
                    foreach ($users as $user) {
4398
                        $user_id = UserManager::get_user_id_from_username($user);
4399
                        if ($user_id !== false) {
4400
                            $userList[] = $user_id;
4401
                            // Insert new users.
4402
                            $sql = "INSERT IGNORE INTO $tbl_session_user SET
4403
                                    user_id = '$user_id',
4404
                                    session_id = '$session_id',
4405
                                    registered_at = '" . api_get_utc_datetime() . "'";
4406
                            Database::query($sql);
4407
                            if ($debug) {
4408
                                $logger->addInfo("Sessions - Adding User #$user_id ($user) to session #$session_id");
4409
                            }
4410
                            $user_counter++;
4411
                        }
4412
                    }
4413
                }
4414
4415
                if ($deleteUsersNotInList) {
4416
                    // Getting user in DB in order to compare to the new list.
4417
                    $usersListInDatabase = self::get_users_by_session($session_id, 0);
4418
4419
                    if (!empty($usersListInDatabase)) {
4420
                        if (empty($userList)) {
4421
                            foreach ($usersListInDatabase as $userInfo) {
4422
                                self::unsubscribe_user_from_session($session_id, $userInfo['user_id']);
4423
                            }
4424
                        } else {
4425
                            foreach ($usersListInDatabase as $userInfo) {
4426
                                if (!in_array($userInfo['user_id'], $userList)) {
4427
                                    self::unsubscribe_user_from_session($session_id, $userInfo['user_id']);
4428
                                }
4429
                            }
4430
                        }
4431
                    }
4432
                }
4433
4434
                $courses = explode('|', $enreg['Courses']);
4435
4436
                // See BT#6449
4437
                $onlyAddFirstCoachOrTeacher = false;
4438
4439
                if ($sessionWithCoursesModifier) {
4440
                    if (count($courses) >= 2) {
4441
                        // Only first teacher in course session;
4442
                        $onlyAddFirstCoachOrTeacher = true;
4443
4444
                        // Remove all teachers from course.
4445
                        $removeAllTeachersFromCourse = false;
4446
                    }
4447
                }
4448
4449
                foreach ($courses as $course) {
4450
                    $courseArray = bracketsToArray($course);
4451
                    $course_code = $courseArray[0];
4452
4453
                    if (CourseManager::course_exists($course_code)) {
4454
4455
                        $courseInfo = api_get_course_info($course_code);
4456
                        $courseId = $courseInfo['real_id'];
4457
4458
                        // Adding the course to a session.
4459
                        $sql = "INSERT IGNORE INTO $tbl_session_course
4460
                                SET c_id = '$courseId', session_id='$session_id'";
4461
                        Database::query($sql);
4462
4463
                        SessionManager::installCourse($session_id, $courseInfo['real_id']);
4464
4465
                        if ($debug) {
4466
                            $logger->addInfo("Sessions - Adding course '$course_code' to session #$session_id");
4467
                        }
4468
4469
                        $course_counter++;
4470
4471
                        $course_coaches = isset($courseArray[1]) ? $courseArray[1] : null;
4472
                        $course_users   = isset($courseArray[2]) ? $courseArray[2] : null;
4473
4474
                        $course_users   = explode(',', $course_users);
4475
                        $course_coaches = explode(',', $course_coaches);
4476
4477
                        // Checking if the flag is set TeachersWillBeAddedAsCoachInAllCourseSessions (course_edit.php)
4478
                        $addTeachersToSession = true;
4479
4480
                        if (array_key_exists('add_teachers_to_sessions_courses', $courseInfo)) {
4481
                            $addTeachersToSession = $courseInfo['add_teachers_to_sessions_courses'];
4482
                        }
4483
4484
                        // If any user provided for a course, use the users array.
4485
                        if (empty($course_users)) {
4486
                            if (!empty($userList)) {
4487
                                SessionManager::subscribe_users_to_session_course(
4488
                                    $userList,
4489
                                    $session_id,
4490
                                    $course_code
4491
                                );
4492
                                if ($debug) {
4493
                                    $msg = "Sessions - Adding student list ".implode(', #', $userList)." to course: '$course_code' and session #$session_id";
4494
                                    $logger->addInfo($msg);
4495
                                }
4496
                            }
4497
                        }
4498
4499
                        // Adding coaches to session course user.
4500
                        if (!empty($course_coaches)) {
4501
                            $savedCoaches = array();
4502
                            // only edit if add_teachers_to_sessions_courses is set.
4503
                            if ($addTeachersToSession) {
4504
                                if ($addOriginalCourseTeachersAsCourseSessionCoaches) {
4505
                                    // Adding course teachers as course session teachers.
4506
                                    $alreadyAddedTeachers = CourseManager::get_teacher_list_from_course_code(
4507
                                        $course_code
4508
                                    );
4509
4510
                                    if (!empty($alreadyAddedTeachers)) {
4511
                                        $teachersToAdd = array();
4512
                                        foreach ($alreadyAddedTeachers as $user) {
4513
                                            $teachersToAdd[] = $user['username'];
4514
                                        }
4515
                                        $course_coaches = array_merge(
4516
                                            $course_coaches,
4517
                                            $teachersToAdd
4518
                                        );
4519
                                    }
4520
                                }
4521
4522 View Code Duplication
                                foreach ($course_coaches as $course_coach) {
4523
                                    $coach_id = UserManager::get_user_id_from_username($course_coach);
4524
                                    if ($coach_id !== false) {
4525
                                        // Just insert new coaches
4526
                                        SessionManager::updateCoaches($session_id, $courseId, array($coach_id), false);
4527
4528
                                        if ($debug) {
4529
                                            $logger->addInfo("Sessions - Adding course coach: user #$coach_id ($course_coach) to course: '$course_code' and session #$session_id");
4530
                                        }
4531
                                        $savedCoaches[] = $coach_id;
4532
                                    } else {
4533
                                        $error_message .= get_lang('UserDoesNotExist').' : '.$course_coach.$eol;
4534
                                    }
4535
                                }
4536
                            }
4537
4538
                            // Custom courses/session coaches
4539
                            $teacherToAdd = null;
4540
                            // Only one coach is added.
4541
                            if ($onlyAddFirstCoachOrTeacher == true) {
4542
4543 View Code Duplication
                                foreach ($course_coaches as $course_coach) {
4544
                                    $coach_id = UserManager::get_user_id_from_username($course_coach);
4545
                                    if ($coach_id !== false) {
4546
                                        $teacherToAdd = $coach_id;
4547
                                        break;
4548
                                    }
4549
                                }
4550
4551
                                // Un subscribe everyone that's not in the list.
4552
                                $teacherList = CourseManager::get_teacher_list_from_course_code($course_code);
4553 View Code Duplication
                                if (!empty($teacherList)) {
4554
                                    foreach ($teacherList as $teacher) {
4555
                                        if ($teacherToAdd != $teacher['user_id']) {
4556
4557
                                            $sql = "SELECT * FROM ".Database::get_main_table(TABLE_MAIN_COURSE_USER)."
4558
                                                    WHERE
4559
                                                        user_id = ".$teacher['user_id']." AND
4560
                                                        course_code = '".$course_code."'
4561
                                                    ";
4562
4563
                                            $result = Database::query($sql);
4564
                                            $userCourseData = Database::fetch_array($result, 'ASSOC');
4565
                                            $teacherBackupList[$teacher['user_id']][$course_code] = $userCourseData;
4566
4567
                                            $sql = "SELECT * FROM ".Database::get_course_table(TABLE_GROUP_USER)."
4568
                                                    WHERE
4569
                                                        user_id = ".$teacher['user_id']." AND
4570
                                                        c_id = '".$courseInfo['real_id']."'
4571
                                                    ";
4572
4573
                                            $result = Database::query($sql);
4574
                                            while ($groupData = Database::fetch_array($result, 'ASSOC')) {
4575
                                                $groupBackup['user'][$teacher['user_id']][$course_code][$groupData['group_id']] = $groupData;
4576
                                            }
4577
4578
                                            $sql = "SELECT * FROM ".Database::get_course_table(TABLE_GROUP_TUTOR)."
4579
                                                    WHERE
4580
                                                        user_id = ".$teacher['user_id']." AND
4581
                                                        c_id = '".$courseInfo['real_id']."'
4582
                                                    ";
4583
4584
                                            $result = Database::query($sql);
4585
                                            while ($groupData = Database::fetch_array($result, 'ASSOC')) {
4586
                                                $groupBackup['tutor'][$teacher['user_id']][$course_code][$groupData['group_id']] = $groupData;
4587
                                            }
4588
4589
                                            CourseManager::unsubscribe_user(
4590
                                                $teacher['user_id'],
4591
                                                $course_code
4592
                                            );
4593
                                        }
4594
                                    }
4595
                                }
4596
4597
                                if (!empty($teacherToAdd)) {
4598
                                    SessionManager::updateCoaches($session_id, $courseId, array($teacherToAdd), true);
4599
4600
                                    $userCourseCategory = '';
4601 View Code Duplication
                                    if (isset($teacherBackupList[$teacherToAdd]) &&
4602
                                        isset($teacherBackupList[$teacherToAdd][$course_code])
4603
                                    ) {
4604
                                        $courseUserData = $teacherBackupList[$teacherToAdd][$course_code];
4605
                                        $userCourseCategory = $courseUserData['user_course_cat'];
4606
                                    }
4607
4608
                                    CourseManager::subscribe_user(
4609
                                        $teacherToAdd,
4610
                                        $course_code,
4611
                                        COURSEMANAGER,
4612
                                        0,
4613
                                        $userCourseCategory
4614
                                    );
4615
4616 View Code Duplication
                                    if (isset($groupBackup['user'][$teacherToAdd]) &&
4617
                                        isset($groupBackup['user'][$teacherToAdd][$course_code]) &&
4618
                                        !empty($groupBackup['user'][$teacherToAdd][$course_code])
4619
                                    ) {
4620
                                        foreach ($groupBackup['user'][$teacherToAdd][$course_code] as $data) {
4621
                                            GroupManager::subscribe_users(
4622
                                                $teacherToAdd,
4623
                                                $data['group_id'],
4624
                                                $data['c_id']
4625
                                            );
4626
                                        }
4627
                                    }
4628
4629 View Code Duplication
                                    if (isset($groupBackup['tutor'][$teacherToAdd]) &&
4630
                                        isset($groupBackup['tutor'][$teacherToAdd][$course_code]) &&
4631
                                        !empty($groupBackup['tutor'][$teacherToAdd][$course_code])
4632
                                    ) {
4633
                                        foreach ($groupBackup['tutor'][$teacherToAdd][$course_code] as $data) {
4634
                                            GroupManager::subscribe_tutors(
4635
                                                $teacherToAdd,
4636
                                                $data['group_id'],
4637
                                                $data['c_id']
4638
                                            );
4639
                                        }
4640
                                    }
4641
                                }
4642
                            }
4643
4644
                            // See BT#6449#note-195
4645
                            // All coaches are added.
4646
                            if ($removeAllTeachersFromCourse) {
4647
                                $teacherToAdd = null;
4648 View Code Duplication
                                foreach ($course_coaches as $course_coach) {
4649
                                    $coach_id = UserManager::get_user_id_from_username(
4650
                                        $course_coach
4651
                                    );
4652
                                    if ($coach_id !== false) {
4653
                                        $teacherToAdd[] = $coach_id;
4654
                                    }
4655
                                }
4656
4657
                                if (!empty($teacherToAdd)) {
4658
                                    // Deleting all course teachers and adding the only coach as teacher.
4659
                                    $teacherList = CourseManager::get_teacher_list_from_course_code($course_code);
4660
4661 View Code Duplication
                                    if (!empty($teacherList)) {
4662
                                        foreach ($teacherList as $teacher) {
4663
                                            if (!in_array($teacher['user_id'], $teacherToAdd)) {
4664
4665
                                                $sql = "SELECT * FROM ".Database::get_main_table(TABLE_MAIN_COURSE_USER)."
4666
                                                        WHERE
4667
                                                            user_id = ".$teacher['user_id']." AND
4668
                                                            course_code = '".$course_code."'
4669
                                                        ";
4670
4671
                                                $result = Database::query($sql);
4672
                                                $userCourseData = Database::fetch_array($result, 'ASSOC');
4673
                                                $teacherBackupList[$teacher['user_id']][$course_code] = $userCourseData;
4674
4675
                                                $sql = "SELECT * FROM ".Database::get_course_table(TABLE_GROUP_USER)."
4676
                                                    WHERE
4677
                                                        user_id = ".$teacher['user_id']." AND
4678
                                                        c_id = '".$courseInfo['real_id']."'
4679
                                                    ";
4680
4681
                                                $result = Database::query($sql);
4682
                                                while ($groupData = Database::fetch_array($result, 'ASSOC')) {
4683
                                                    $groupBackup['user'][$teacher['user_id']][$course_code][$groupData['group_id']] = $groupData;
4684
                                                }
4685
4686
                                                $sql = "SELECT * FROM ".Database::get_course_table(TABLE_GROUP_TUTOR)."
4687
                                                        WHERE
4688
                                                            user_id = ".$teacher['user_id']." AND
4689
                                                            c_id = '".$courseInfo['real_id']."'
4690
                                                        ";
4691
4692
                                                $result = Database::query($sql);
4693
                                                while ($groupData = Database::fetch_array($result, 'ASSOC')) {
4694
                                                    $groupBackup['tutor'][$teacher['user_id']][$course_code][$groupData['group_id']] = $groupData;
4695
                                                }
4696
4697
                                                CourseManager::unsubscribe_user(
4698
                                                    $teacher['user_id'],
4699
                                                    $course_code
4700
                                                );
4701
                                            }
4702
                                        }
4703
                                    }
4704
4705
                                    foreach ($teacherToAdd as $teacherId) {
4706
                                        $userCourseCategory = '';
4707 View Code Duplication
                                        if (isset($teacherBackupList[$teacherId]) &&
4708
                                            isset($teacherBackupList[$teacherId][$course_code])
4709
                                        ) {
4710
                                            $courseUserData = $teacherBackupList[$teacherId][$course_code];
4711
                                            $userCourseCategory = $courseUserData['user_course_cat'];
4712
                                        }
4713
4714
                                        CourseManager::subscribe_user(
4715
                                            $teacherId,
4716
                                            $course_code,
4717
                                            COURSEMANAGER,
4718
                                            0,
4719
                                            $userCourseCategory
4720
                                        );
4721
4722 View Code Duplication
                                        if (isset($groupBackup['user'][$teacherId]) &&
4723
                                            isset($groupBackup['user'][$teacherId][$course_code]) &&
4724
                                            !empty($groupBackup['user'][$teacherId][$course_code])
4725
                                        ) {
4726
                                            foreach ($groupBackup['user'][$teacherId][$course_code] as $data) {
4727
                                                GroupManager::subscribe_users(
4728
                                                    $teacherId,
4729
                                                    $data['group_id'],
4730
                                                    $data['c_id']
4731
                                                );
4732
                                            }
4733
                                        }
4734
4735 View Code Duplication
                                        if (isset($groupBackup['tutor'][$teacherId]) &&
4736
                                            isset($groupBackup['tutor'][$teacherId][$course_code]) &&
4737
                                            !empty($groupBackup['tutor'][$teacherId][$course_code])
4738
                                        ) {
4739
                                            foreach ($groupBackup['tutor'][$teacherId][$course_code] as $data) {
4740
                                                GroupManager::subscribe_tutors(
4741
                                                    $teacherId,
4742
                                                    $data['group_id'],
4743
                                                    $data['c_id']
4744
                                                );
4745
                                            }
4746
                                        }
4747
                                    }
4748
                                }
4749
                            }
4750
4751
                            // Continue default behaviour.
4752
                            if ($onlyAddFirstCoachOrTeacher == false) {
4753
                                // Checking one more time see BT#6449#note-149
4754
                                $coaches = SessionManager::getCoachesByCourseSession($session_id, $courseId);
4755
                                // Update coaches if only there's 1 course see BT#6449#note-189
4756
                                if (empty($coaches) || count($courses) == 1) {
4757 View Code Duplication
                                    foreach ($course_coaches as $course_coach) {
4758
                                        $course_coach = trim($course_coach);
4759
                                        $coach_id = UserManager::get_user_id_from_username($course_coach);
4760
                                        if ($coach_id !== false) {
4761
                                            // Just insert new coaches
4762
                                            SessionManager::updateCoaches(
4763
                                                $session_id,
4764
                                                $courseId,
4765
                                                array($coach_id),
4766
                                                false
4767
                                            );
4768
4769
                                            if ($debug) {
4770
                                                $logger->addInfo("Sessions - Adding course coach: user #$coach_id ($course_coach) to course: '$course_code' and session #$session_id");
4771
                                            }
4772
                                            $savedCoaches[] = $coach_id;
4773
                                        } else {
4774
                                            $error_message .= get_lang('UserDoesNotExist').' : '.$course_coach.$eol;
4775
                                        }
4776
                                    }
4777
                                }
4778
                            }
4779
                        }
4780
4781
                        // Adding Students, updating relationship "Session - Course - User".
4782
                        $course_users = array_filter($course_users);
4783
4784
                        if (!empty($course_users)) {
4785 View Code Duplication
                            foreach ($course_users as $user) {
4786
                                $user_id = UserManager::get_user_id_from_username($user);
4787
4788
                                if ($user_id !== false) {
4789
                                    SessionManager::subscribe_users_to_session_course(
4790
                                        array($user_id),
4791
                                        $session_id,
4792
                                        $course_code
4793
                                    );
4794
                                    if ($debug) {
4795
                                        $logger->addInfo("Sessions - Adding student: user #$user_id ($user) to course: '$course_code' and session #$session_id");
4796
                                    }
4797
                                } else {
4798
                                    $error_message .= get_lang('UserDoesNotExist').': '.$user.$eol;
4799
                                }
4800
                            }
4801
                        }
4802
4803
                        $inserted_in_course[$course_code] = $courseInfo['title'];
4804
                    }
4805
                }
4806
                $access_url_id = api_get_current_access_url_id();
4807
                UrlManager::add_session_to_url($session_id, $access_url_id);
4808
                $sql = "UPDATE $tbl_session SET nbr_users = '$user_counter', nbr_courses = '$course_counter' WHERE id = '$session_id'";
4809
                Database::query($sql);
4810
            }
4811
        }
4812
4813
        return array(
4814
            'error_message' => $error_message,
4815
            'session_counter' => $session_counter,
4816
            'session_list' => $sessionList,
4817
        );
4818
    }
4819
4820
    /**
4821
     * @param int $sessionId
4822
     * @param int $courseId
4823
     * @return array
4824
     */
4825 View Code Duplication
    public static function getCoachesByCourseSession($sessionId, $courseId)
4826
    {
4827
        $table = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
4828
        $sessionId = intval($sessionId);
4829
        $courseId = intval($courseId);
4830
4831
        $sql = "SELECT user_id FROM $table
4832
                WHERE
4833
                    session_id = '$sessionId' AND
4834
                    c_id = '$courseId' AND
4835
                    status = 2";
4836
        $result = Database::query($sql);
4837
4838
        $coaches = array();
4839
        if (Database::num_rows($result) > 0) {
4840
            while ($row = Database::fetch_row($result)) {
4841
                $coaches[] = $row[0];
4842
            }
4843
        }
4844
4845
        return $coaches;
4846
    }
4847
4848
    /**
4849
     * @param int $sessionId
4850
     * @param int $courseId
4851
     * @return string
4852
     */
4853
    public static function getCoachesByCourseSessionToString(
4854
        $sessionId,
4855
        $courseId
4856
    ) {
4857
        $coaches = self::getCoachesByCourseSession($sessionId, $courseId);
4858
        $list = array();
4859 View Code Duplication
        if (!empty($coaches)) {
4860
            foreach ($coaches as $coachId) {
4861
                $userInfo = api_get_user_info($coachId);
4862
                $list[] = api_get_person_name(
4863
                    $userInfo['firstname'],
4864
                    $userInfo['lastname']
4865
                );
4866
            }
4867
        }
4868
4869
        return array_to_string($list, CourseManager::USER_SEPARATOR);
4870
    }
4871
4872
    /**
4873
     * Get all coaches added in the session - course relationship
4874
     * @param int $sessionId
4875
     * @return array
4876
     */
4877
    public static function getCoachesBySession($sessionId)
4878
    {
4879
        $table = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
4880
        $sessionId = intval($sessionId);
4881
4882
        $sql = "SELECT DISTINCT user_id
4883
                FROM $table
4884
                WHERE session_id = '$sessionId' AND status = 2";
4885
        $result = Database::query($sql);
4886
4887
        $coaches = array();
4888
        if (Database::num_rows($result) > 0) {
4889
            while ($row = Database::fetch_array($result)) {
4890
                $coaches[] = $row['user_id'];
4891
            }
4892
        }
4893
4894
        return $coaches;
4895
    }
4896
4897
    /**
4898
     * @param int $userId
4899
     * @return array
4900
     */
4901
    public static function getAllCoursesFromAllSessionFromDrh($userId)
4902
    {
4903
        $sessions = SessionManager::get_sessions_followed_by_drh($userId);
4904
        $coursesFromSession = array();
4905
        if (!empty($sessions)) {
4906
            foreach ($sessions as $session) {
4907
                $courseList = SessionManager::get_course_list_by_session_id($session['id']);
4908
                foreach ($courseList as $course) {
0 ignored issues
show
Bug introduced by
The expression $courseList of type integer|array is not guaranteed to be traversable. How about adding an additional type check?

There are different options of fixing this problem.

  1. If you want to be on the safe side, you can add an additional type-check:

    $collection = json_decode($data, true);
    if ( ! is_array($collection)) {
        throw new \RuntimeException('$collection must be an array.');
    }
    
    foreach ($collection as $item) { /** ... */ }
    
  2. If you are sure that the expression is traversable, you might want to add a doc comment cast to improve IDE auto-completion and static analysis:

    /** @var array $collection */
    $collection = json_decode($data, true);
    
    foreach ($collection as $item) { /** .. */ }
    
  3. Mark the issue as a false-positive: Just hover the remove button, in the top-right corner of this issue for more options.

Loading history...
4909
                    $coursesFromSession[] = $course['code'];
4910
                }
4911
            }
4912
        }
4913
        return $coursesFromSession;
4914
    }
4915
4916
    /**
4917
     * @param string $status
4918
     * @param int $userId
4919
     * @param bool $getCount
4920
     * @param int  $from
4921
     * @param int  $numberItems
4922
     * @param int $column
4923
     * @param string $direction
4924
     * @param string $keyword
4925
     * @param string $active
4926
     * @param string $lastConnectionDate
4927
     * @param array $sessionIdList
4928
     * @param array $studentIdList
4929
     * @param int $filterByStatus
4930
     * @return array|int
4931
     */
4932
    public static function getAllUsersFromCoursesFromAllSessionFromStatus(
4933
        $status,
4934
        $userId,
4935
        $getCount = false,
4936
        $from = null,
4937
        $numberItems = null,
4938
        $column = 1,
4939
        $direction = 'asc',
4940
        $keyword = null,
4941
        $active = null,
4942
        $lastConnectionDate = null,
4943
        $sessionIdList = array(),
4944
        $studentIdList = array(),
4945
        $filterByStatus = null
4946
    ) {
4947
        $filterByStatus = intval($filterByStatus);
4948
4949
        $tbl_user = Database::get_main_table(TABLE_MAIN_USER);
4950
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
4951
        $tbl_course = Database::get_main_table(TABLE_MAIN_COURSE);
4952
        $tbl_course_user = Database::get_main_table(TABLE_MAIN_COURSE_USER);
4953
        $tbl_course_rel_access_url = Database::get_main_table(TABLE_MAIN_ACCESS_URL_REL_COURSE);
4954
        $tbl_session_rel_course_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
4955
        $tbl_session_rel_access_url = Database::get_main_table(TABLE_MAIN_ACCESS_URL_REL_SESSION);
4956
4957
        $direction = in_array(strtolower($direction), array('asc', 'desc')) ? $direction : 'asc';
4958
        $column = Database::escape_string($column);
4959
        $userId = intval($userId);
4960
4961
        $limitCondition = null;
4962
4963 View Code Duplication
        if (isset($from) && isset($numberItems)) {
4964
            $from = intval($from);
4965
            $numberItems = intval($numberItems);
4966
            $limitCondition = "LIMIT $from, $numberItems";
4967
        }
4968
4969
        $urlId = api_get_current_access_url_id();
4970
4971
        $sessionConditions = null;
4972
        $courseConditions = null;
4973
        $userConditions = null;
4974
4975
        if (isset($active)) {
4976
            $active = intval($active);
4977
            $userConditions .= " AND active = $active";
4978
        }
4979
4980
        switch ($status) {
4981
            case 'drh':
4982
                // Classic DRH
4983
                if (empty($studentIdList)) {
4984
                    $studentListSql = UserManager::get_users_followed_by_drh(
4985
                        $userId,
4986
                        $filterByStatus,
4987
                        true,
4988
                        false
4989
                    );
4990
                    $studentIdList = array_keys($studentListSql);
4991
                    $studentListSql = "'".implode("','", $studentIdList)."'";
4992
                } else {
4993
                    $studentIdList = array_map('intval', $studentIdList);
4994
                    $studentListSql = "'".implode("','", $studentIdList)."'";
4995
                }
4996
                if (!empty($studentListSql)) {
4997
                    $userConditions = " AND u.user_id IN (".$studentListSql.") ";
4998
                }
4999
                break;
5000
            case 'drh_all':
5001
                // Show all by DRH
5002
                if (empty($sessionIdList)) {
5003
                    $sessionsListSql = SessionManager::get_sessions_followed_by_drh(
5004
                        $userId,
5005
                        null,
5006
                        null,
5007
                        false,
5008
                        true,
5009
                        true
5010
                    );
5011
                } else {
5012
                    $sessionIdList = array_map('intval', $sessionIdList);
5013
                    $sessionsListSql = "'".implode("','", $sessionIdList)."'";
5014
                }
5015
                if (!empty($sessionsListSql)) {
5016
                    $sessionConditions = " AND s.id IN (".$sessionsListSql.") ";
5017
                }
5018
                break;
5019
            case 'session_admin';
0 ignored issues
show
Coding Style introduced by
case statements should be defined using a colon.

As per the PSR-2 coding standard, case statements should not be wrapped in curly braces. There is no need for braces, since each case is terminated by the next break.

There is also the option to use a semicolon instead of a colon, this is discouraged because many programmers do not even know it works and the colon is universal between programming languages.

switch ($expr) {
    case "A": { //wrong
        doSomething();
        break;
    }
    case "B"; //wrong
        doSomething();
        break;
    case "C": //right
        doSomething();
        break;
}

To learn more about the PSR-2 coding standard, please refer to the PHP-Fig.

Loading history...
5020
                $sessionConditions = " AND s.id_coach = $userId ";
5021
                break;
5022
            case 'admin':
5023
                break;
5024
            case 'teacher':
5025
                $sessionConditions = " AND s.id_coach = $userId ";
5026
                break;
5027
        }
5028
5029
        $select = "SELECT DISTINCT u.* ";
5030
        $masterSelect = "SELECT DISTINCT * FROM ";
5031
5032
        if ($getCount) {
5033
            $select = "SELECT DISTINCT u.user_id ";
5034
            $masterSelect = "SELECT COUNT(DISTINCT(user_id)) as count FROM ";
5035
        }
5036
5037
        if (!empty($filterByStatus)) {
5038
            $userConditions .= " AND u.status = ".$filterByStatus;
5039
        }
5040
5041
        if (!empty($lastConnectionDate)) {
5042
            $lastConnectionDate = Database::escape_string($lastConnectionDate);
5043
            $userConditions .=  " AND u.last_login <= '$lastConnectionDate' ";
5044
        }
5045
5046 View Code Duplication
        if (!empty($keyword)) {
5047
            $keyword = Database::escape_string($keyword);
5048
            $userConditions .= " AND (
5049
                u.username LIKE '%$keyword%' OR
5050
                u.firstname LIKE '%$keyword%' OR
5051
                u.lastname LIKE '%$keyword%' OR
5052
                u.official_code LIKE '%$keyword%' OR
5053
                u.email LIKE '%$keyword%'
5054
            )";
5055
        }
5056
5057
        $where = " WHERE
5058
                   access_url_id = $urlId
5059
                   $userConditions
5060
        ";
5061
5062
        $sql = "$masterSelect (
5063
                ($select
5064
                FROM $tbl_session s
5065
                    INNER JOIN $tbl_session_rel_course_rel_user su ON (s.id = su.session_id)
5066
                    INNER JOIN $tbl_user u ON (u.user_id = su.user_id)
5067
                    INNER JOIN $tbl_session_rel_access_url url ON (url.session_id = s.id)
5068
                    $where
5069
                    $sessionConditions
5070
                )
5071
                UNION (
5072
                    $select
5073
                    FROM $tbl_course c
5074
                    INNER JOIN $tbl_course_user cu ON (cu.c_id = c.id)
5075
                    INNER JOIN $tbl_user u ON (u.user_id = cu.user_id)
5076
                    INNER JOIN $tbl_course_rel_access_url url ON (url.c_id = c.id)
5077
                    $where
5078
                    $courseConditions
5079
                )
5080
                ) as t1
5081
                ";
5082
5083
        if ($getCount) {
5084
            $result = Database::query($sql);
5085
            $count = 0;
5086
            if (Database::num_rows($result)) {
5087
                $rows = Database::fetch_array($result);
5088
                $count = $rows['count'];
5089
            }
5090
            return $count;
5091
        }
5092
5093 View Code Duplication
        if (!empty($column) && !empty($direction)) {
5094
            $column = str_replace('u.', '', $column);
5095
            $sql .= " ORDER BY $column $direction ";
5096
        }
5097
5098
        $sql .= $limitCondition;
5099
        $result = Database::query($sql);
5100
        $result = Database::store_result($result);
0 ignored issues
show
Bug introduced by
It seems like $result can be null; however, store_result() does not accept null, maybe add an additional type check?

Unless you are absolutely sure that the expression can never be null because of other conditions, we strongly recommend to add an additional type check to your code:

/** @return stdClass|null */
function mayReturnNull() { }

function doesNotAcceptNull(stdClass $x) { }

// With potential error.
function withoutCheck() {
    $x = mayReturnNull();
    doesNotAcceptNull($x); // Potential error here.
}

// Safe - Alternative 1
function withCheck1() {
    $x = mayReturnNull();
    if ( ! $x instanceof stdClass) {
        throw new \LogicException('$x must be defined.');
    }
    doesNotAcceptNull($x);
}

// Safe - Alternative 2
function withCheck2() {
    $x = mayReturnNull();
    if ($x instanceof stdClass) {
        doesNotAcceptNull($x);
    }
}
Loading history...
5101
5102
        return $result ;
5103
    }
5104
5105
    /**
5106
     * @param int $sessionId
5107
     * @param int $courseId
5108
     * @param array $coachList
5109
     * @param bool $deleteCoachesNotInList
5110
     */
5111
    public static function updateCoaches(
5112
        $sessionId,
5113
        $courseId,
5114
        $coachList,
5115
        $deleteCoachesNotInList = false
5116
    ) {
5117
        $currentCoaches = self::getCoachesByCourseSession($sessionId, $courseId);
5118
5119
        if (!empty($coachList)) {
5120
            foreach ($coachList as $userId) {
5121
                self::set_coach_to_course_session($userId, $sessionId, $courseId);
5122
            }
5123
        }
5124
5125
        if ($deleteCoachesNotInList) {
5126
            if (!empty($coachList)) {
5127
                $coachesToDelete = array_diff($currentCoaches, $coachList);
5128
            } else {
5129
                $coachesToDelete = $currentCoaches;
5130
            }
5131
5132
            if (!empty($coachesToDelete)) {
5133
                foreach ($coachesToDelete as $userId) {
5134
                    self::set_coach_to_course_session(
5135
                        $userId,
5136
                        $sessionId,
5137
                        $courseId,
5138
                        true
5139
                    );
5140
                }
5141
            }
5142
        }
5143
    }
5144
5145
    /**
5146
     * @param array $sessions
5147
     * @param array $sessionsDestination
5148
     * @return string
5149
     */
5150
    public static function copyStudentsFromSession($sessions, $sessionsDestination)
5151
    {
5152
        $messages = array();
5153
        if (!empty($sessions)) {
5154
            foreach ($sessions as $sessionId) {
5155
                $sessionInfo = self::fetch($sessionId);
5156
                $userList = self::get_users_by_session($sessionId, 0);
5157
                if (!empty($userList)) {
5158
                    $newUserList = array();
5159
                    $userToString = null;
5160
                    foreach ($userList as $userInfo) {
5161
                        $newUserList[] = $userInfo['user_id'];
5162
                        $userToString .= $userInfo['firstname'] . ' ' . $userInfo['lastname'] . '<br />';
5163
                    }
5164
5165
                    if (!empty($sessionsDestination)) {
5166
                        foreach ($sessionsDestination as $sessionDestinationId) {
5167
                            $sessionDestinationInfo = self::fetch($sessionDestinationId);
5168
                            $messages[] = Display::return_message(
5169
                                sprintf(get_lang('AddingStudentsFromSessionXToSessionY'), $sessionInfo['name'], $sessionDestinationInfo['name']), 'info', false
5170
                            );
5171
                            if ($sessionId == $sessionDestinationId) {
5172
                                $messages[] = Display::return_message(sprintf(get_lang('SessionXSkipped'), $sessionDestinationId), 'warning', false);
5173
                                continue;
5174
                            }
5175
                            $messages[] = Display::return_message(get_lang('StudentList') . '<br />' . $userToString, 'info', false);
5176
                            SessionManager::suscribe_users_to_session(
5177
                                $sessionDestinationId,
5178
                                $newUserList,
5179
                                SESSION_VISIBLE_READ_ONLY,
5180
                                false
5181
                            );
5182
                        }
5183
                    } else {
5184
                        $messages[] = Display::return_message(get_lang('NoDestinationSessionProvided'), 'warning');
5185
                    }
5186
                } else {
5187
                    $messages[] = Display::return_message(
5188
                        get_lang('NoStudentsFoundForSession').' #'.$sessionInfo['name'],
5189
                        'warning'
5190
                    );
5191
                }
5192
            }
5193
        } else {
5194
            $messages[] = Display::return_message(get_lang('NoData'), 'warning');
5195
        }
5196
        return $messages;
5197
    }
5198
5199
    /**
5200
     * Assign coaches of a session(s) as teachers to a given course (or courses)
5201
     * @param array A list of session IDs
5202
     * @param array A list of course IDs
5203
     * @return string
5204
     */
5205
    public static function copyCoachesFromSessionToCourse($sessions, $courses)
5206
    {
5207
        $coachesPerSession = array();
5208
        foreach ($sessions as $sessionId) {
5209
            $coaches = self::getCoachesBySession($sessionId);
5210
            $coachesPerSession[$sessionId] = $coaches;
5211
        }
5212
5213
        $result = array();
5214
5215
        if (!empty($courses)) {
5216
            foreach ($courses as $courseId) {
5217
                $courseInfo = api_get_course_info_by_id($courseId);
5218
                foreach ($coachesPerSession as $sessionId => $coachList) {
5219
                    CourseManager::updateTeachers(
5220
                        $courseInfo['real_id'], $coachList, false, false, false
5221
                    );
5222
                    $result[$courseInfo['code']][$sessionId] = $coachList;
5223
                }
5224
            }
5225
        }
5226
        $sessionUrl = api_get_path(WEB_CODE_PATH) . 'admin/resume_session.php?id_session=';
5227
5228
        $htmlResult = null;
5229
5230
        if (!empty($result)) {
5231
            foreach ($result as $courseCode => $data) {
5232
                $url = api_get_course_url($courseCode);
5233
                $htmlResult .= sprintf(
5234
                    get_lang('CoachesSubscribedAsATeacherInCourseX'),
5235
                    Display::url($courseCode, $url, array('target' => '_blank'))
5236
                );
5237
                foreach ($data as $sessionId => $coachList) {
5238
                    $sessionInfo = self::fetch($sessionId);
5239
                    $htmlResult .= '<br />';
5240
                    $htmlResult .= Display::url(
5241
                        get_lang('Session') . ': ' . $sessionInfo['name'] . ' <br />', $sessionUrl . $sessionId, array('target' => '_blank')
5242
                    );
5243
                    $teacherList = array();
5244
                    foreach ($coachList as $coachId) {
5245
                        $userInfo = api_get_user_info($coachId);
5246
                        $teacherList[] = $userInfo['complete_name'];
5247
                    }
5248
                    if (!empty($teacherList)) {
5249
                        $htmlResult .= implode(', ', $teacherList);
5250
                    } else {
5251
                        $htmlResult .= get_lang('NothingToAdd');
5252
                    }
5253
                }
5254
                $htmlResult .= '<br />';
5255
            }
5256
            $htmlResult = Display::return_message($htmlResult, 'normal', false);
5257
        }
5258
        return $htmlResult;
5259
    }
5260
5261
    /**
5262
     * @param string $keyword
5263
     * @param string $active
5264
     * @param string $lastConnectionDate
5265
     * @param array $sessionIdList
5266
     * @param array $studentIdList
5267
     * @param int $userStatus STUDENT|COURSEMANAGER constants
0 ignored issues
show
Documentation introduced by
There is no parameter named $userStatus. Did you maybe mean $filterUserStatus?

This check looks for PHPDoc comments describing methods or function parameters that do not exist on the corresponding method or function. It has, however, found a similar but not annotated parameter which might be a good fit.

Consider the following example. The parameter $ireland is not defined by the method finale(...).

/**
 * @param array $germany
 * @param array $ireland
 */
function finale($germany, $island) {
    return "2:1";
}

The most likely cause is that the parameter was changed, but the annotation was not.

Loading history...
5268
     *
5269
     * @return array|int
5270
     */
5271
    public static function getCountUserTracking(
5272
        $keyword = null,
5273
        $active = null,
5274
        $lastConnectionDate = null,
5275
        $sessionIdList = array(),
5276
        $studentIdList = array(),
5277
        $filterUserStatus = null
5278
    ) {
5279
        $userId = api_get_user_id();
5280
        $drhLoaded = false;
5281
5282
        if (api_is_drh()) {
5283
            if (api_drh_can_access_all_session_content()) {
5284
                $count = self::getAllUsersFromCoursesFromAllSessionFromStatus(
5285
                    'drh_all',
5286
                    $userId,
5287
                    true,
5288
                    null,
5289
                    null,
5290
                    null,
5291
                    null,
5292
                    $keyword,
5293
                    $active,
5294
                    $lastConnectionDate,
5295
                    $sessionIdList,
5296
                    $studentIdList,
5297
                    $filterUserStatus
5298
                );
5299
                $drhLoaded = true;
5300
            }
5301
        }
5302
5303
        if ($drhLoaded == false) {
5304
            $count = UserManager::getUsersFollowedByUser(
5305
                $userId,
5306
                $filterUserStatus,
5307
                false,
5308
                false,
5309
                true,
5310
                null,
5311
                null,
5312
                null,
5313
                null,
5314
                $active,
5315
                $lastConnectionDate,
5316
                api_is_student_boss() ? STUDENT_BOSS : COURSEMANAGER,
5317
                $keyword
5318
            );
5319
        }
5320
5321
        return $count;
5322
    }
5323
5324
    /**
5325
     * Get teachers followed by a user
5326
     * @param int $userId
5327
     * @param int $active
5328
     * @param string $lastConnectionDate
5329
     * @param bool $getCount
5330
     * @param array $sessionIdList
5331
     * @return array|int
5332
     */
5333
    public static function getTeacherTracking(
5334
        $userId,
5335
        $active = 1,
5336
        $lastConnectionDate = null,
5337
        $getCount = false,
5338
        $sessionIdList = array()
5339
    ) {
5340
        $teacherListId = array();
5341
5342
        if (api_is_drh() || api_is_platform_admin()) {
5343
            // Followed teachers by drh
5344
            if (api_drh_can_access_all_session_content()) {
5345
                if (empty($sessionIdList)) {
5346
                    $sessions = SessionManager::get_sessions_followed_by_drh($userId);
5347
                    $sessionIdList = array();
5348
                    foreach ($sessions as $session) {
5349
                        $sessionIdList[] = $session['id'];
5350
                    }
5351
                }
5352
5353
                $sessionIdList = array_map('intval', $sessionIdList);
5354
                $sessionToString = implode("', '",  $sessionIdList);
5355
5356
                $course = Database::get_main_table(TABLE_MAIN_COURSE);
5357
                $sessionCourse = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
5358
                $courseUser = Database::get_main_table(TABLE_MAIN_COURSE_USER);
5359
5360
                // Select the teachers.
5361
                $sql = "SELECT DISTINCT(cu.user_id) FROM $course c
5362
                        INNER JOIN $sessionCourse src ON c.id = src.c_id
5363
                        INNER JOIN $courseUser cu ON (cu.c_id = c.id)
5364
		                WHERE src.session_id IN ('$sessionToString') AND cu.status = 1";
5365
                $result = Database::query($sql);
5366
                while($row = Database::fetch_array($result, 'ASSOC')) {
5367
                    $teacherListId[$row['user_id']] = $row['user_id'];
5368
                }
5369
            } else {
5370
                $teacherResult = UserManager::get_users_followed_by_drh($userId, COURSEMANAGER);
5371
                foreach ($teacherResult as $userInfo) {
5372
                    $teacherListId[] = $userInfo['user_id'];
5373
                }
5374
            }
5375
        }
5376
5377
        if (!empty($teacherListId)) {
5378
            $tableUser = Database::get_main_table(TABLE_MAIN_USER);
5379
5380
            $select = "SELECT DISTINCT u.* ";
5381
            if ($getCount) {
5382
                $select = "SELECT count(DISTINCT(u.user_id)) as count";
5383
            }
5384
5385
            $sql = "$select FROM $tableUser u";
5386
5387
            if (!empty($lastConnectionDate)) {
5388
                $tableLogin = Database::get_main_table(TABLE_STATISTIC_TRACK_E_LOGIN);
5389
                //$sql .= " INNER JOIN $tableLogin l ON (l.login_user_id = u.user_id) ";
5390
            }
5391
            $active = intval($active);
5392
            $teacherListId = implode("','", $teacherListId);
5393
            $where = " WHERE u.active = $active AND u.user_id IN ('$teacherListId') ";
5394
5395
            if (!empty($lastConnectionDate)) {
5396
                $lastConnectionDate = Database::escape_string($lastConnectionDate);
5397
                //$where .= " AND l.login_date <= '$lastConnectionDate' ";
5398
            }
5399
5400
            $sql .= $where;
5401
            $result = Database::query($sql);
5402
            if (Database::num_rows($result)) {
5403
                if ($getCount) {
5404
                    $row = Database::fetch_array($result);
5405
                    return $row['count'];
5406
                } else {
5407
5408
                    return Database::store_result($result, 'ASSOC');
5409
                }
5410
            }
5411
        }
5412
5413
        return 0;
5414
    }
5415
5416
    /**
5417
     * Get the list of course tools that have to be dealt with in case of
5418
     * registering any course to a session
5419
     * @return array The list of tools to be dealt with (literal names)
5420
     */
5421
    public static function getCourseToolToBeManaged()
5422
    {
5423
        return array(
5424
            'courseDescription',
5425
            'courseIntroduction',
5426
        );
5427
    }
5428
5429
    /**
5430
     * Calls the methods bound to each tool when a course is registered into a session
5431
     * @param int $sessionId
5432
     * @param int $courseId
5433
     * @return void
5434
     */
5435 View Code Duplication
    public static function installCourse($sessionId, $courseId)
5436
    {
5437
        return true;
5438
        $toolList = self::getCourseToolToBeManaged();
0 ignored issues
show
Unused Code introduced by
$toolList = self::getCourseToolToBeManaged(); does not seem to be reachable.

This check looks for unreachable code. It uses sophisticated control flow analysis techniques to find statements which will never be executed.

Unreachable code is most often the result of return, die or exit statements that have been added for debug purposes.

function fx() {
    try {
        doSomething();
        return true;
    }
    catch (\Exception $e) {
        return false;
    }

    return false;
}

In the above example, the last return false will never be executed, because a return statement has already been met in every possible execution path.

Loading history...
5439
5440
        foreach ($toolList as $tool) {
5441
            $method = 'add' . $tool;
5442
            if (method_exists(get_class(), $method)) {
0 ignored issues
show
Bug introduced by
The variable $method seems only to be defined at a later point. Did you maybe move this code here without moving the variable definition?

This error can happen if you refactor code and forget to move the variable initialization.

Let’s take a look at a simple example:

function someFunction() {
    $x = 5;
    echo $x;
}

The above code is perfectly fine. Now imagine that we re-order the statements:

function someFunction() {
    echo $x;
    $x = 5;
}

In that case, $x would be read before it is initialized. This was a very basic example, however the principle is the same for the found issue.

Loading history...
5443
                self::$method($sessionId, $courseId);
5444
            }
5445
        }
5446
    }
5447
5448
    /**
5449
     * Calls the methods bound to each tool when a course is unregistered from
5450
     * a session
5451
     * @param int $sessionId
5452
     * @param int $courseId
5453
     */
5454 View Code Duplication
    public static function unInstallCourse($sessionId, $courseId)
5455
    {
5456
        return true;
5457
        $toolList = self::getCourseToolToBeManaged();
0 ignored issues
show
Unused Code introduced by
$toolList = self::getCourseToolToBeManaged(); does not seem to be reachable.

This check looks for unreachable code. It uses sophisticated control flow analysis techniques to find statements which will never be executed.

Unreachable code is most often the result of return, die or exit statements that have been added for debug purposes.

function fx() {
    try {
        doSomething();
        return true;
    }
    catch (\Exception $e) {
        return false;
    }

    return false;
}

In the above example, the last return false will never be executed, because a return statement has already been met in every possible execution path.

Loading history...
5458
5459
        foreach ($toolList as $tool) {
5460
            $method = 'remove' . $tool;
5461
            if (method_exists(get_class(), $method)) {
0 ignored issues
show
Bug introduced by
The variable $method seems only to be defined at a later point. Did you maybe move this code here without moving the variable definition?

This error can happen if you refactor code and forget to move the variable initialization.

Let’s take a look at a simple example:

function someFunction() {
    $x = 5;
    echo $x;
}

The above code is perfectly fine. Now imagine that we re-order the statements:

function someFunction() {
    echo $x;
    $x = 5;
}

In that case, $x would be read before it is initialized. This was a very basic example, however the principle is the same for the found issue.

Loading history...
5462
                self::$method($sessionId, $courseId);
5463
            }
5464
        }
5465
    }
5466
5467
    /**
5468
     * @param int $sessionId
5469
     * @param int $courseId
5470
     */
5471
    public static function addCourseIntroduction($sessionId, $courseId)
5472
    {
5473
        // @todo create a tool intro lib
5474
        $sessionId = intval($sessionId);
5475
        $courseId = intval($courseId);
5476
5477
        $TBL_INTRODUCTION = Database::get_course_table(TABLE_TOOL_INTRO);
5478
        $sql = "SELECT * FROM $TBL_INTRODUCTION WHERE c_id = $courseId";
5479
        $result = Database::query($sql);
5480
        $result = Database::store_result($result, 'ASSOC');
0 ignored issues
show
Bug introduced by
It seems like $result can be null; however, store_result() does not accept null, maybe add an additional type check?

Unless you are absolutely sure that the expression can never be null because of other conditions, we strongly recommend to add an additional type check to your code:

/** @return stdClass|null */
function mayReturnNull() { }

function doesNotAcceptNull(stdClass $x) { }

// With potential error.
function withoutCheck() {
    $x = mayReturnNull();
    doesNotAcceptNull($x); // Potential error here.
}

// Safe - Alternative 1
function withCheck1() {
    $x = mayReturnNull();
    if ( ! $x instanceof stdClass) {
        throw new \LogicException('$x must be defined.');
    }
    doesNotAcceptNull($x);
}

// Safe - Alternative 2
function withCheck2() {
    $x = mayReturnNull();
    if ($x instanceof stdClass) {
        doesNotAcceptNull($x);
    }
}
Loading history...
5481
5482
        if (!empty($result)) {
5483
            foreach ($result as $result) {
5484
                // @todo check if relation exits.
5485
                $result['session_id'] = $sessionId;
5486
                Database::insert($TBL_INTRODUCTION, $result);
5487
            }
5488
        }
5489
    }
5490
5491
    /**
5492
     * @param int $sessionId
5493
     * @param int $courseId
5494
     */
5495
    public static function removeCourseIntroduction($sessionId, $courseId)
5496
    {
5497
        $sessionId = intval($sessionId);
5498
        $courseId = intval($courseId);
5499
        $TBL_INTRODUCTION = Database::get_course_table(TABLE_TOOL_INTRO);
5500
        $sql = "DELETE FROM $TBL_INTRODUCTION
5501
                WHERE c_id = $courseId AND session_id = $sessionId";
5502
        Database::query($sql);
5503
    }
5504
5505
    /**
5506
     * @param int $sessionId
5507
     * @param int $courseId
5508
     */
5509
    public static function addCourseDescription($sessionId, $courseId)
5510
    {
5511
        /* $description = new CourseDescription();
5512
          $descriptions = $description->get_descriptions($courseId);
5513
          foreach ($descriptions as $description) {
5514
          } */
5515
    }
5516
5517
    /**
5518
     * @param int $sessionId
5519
     * @param int $courseId
5520
     */
5521
    public static function removeCourseDescription($sessionId, $courseId)
5522
    {
5523
5524
    }
5525
5526
    /**
5527
     * @param array $userSessionList format see self::importSessionDrhCSV()
5528
     * @param bool $sendEmail
5529
     * @param bool $removeOldRelationShips
5530
     * @return string
5531
     */
5532
    public static function subscribeDrhToSessionList($userSessionList, $sendEmail, $removeOldRelationShips)
5533
    {
5534
        if (!empty($userSessionList)) {
5535
            foreach ($userSessionList as $userId => $data) {
5536
                $sessionList = array();
5537
                foreach ($data['session_list'] as $sessionInfo) {
5538
                    $sessionList[] = $sessionInfo['session_id'];
5539
                }
5540
                $userInfo = $data['user_info'];
5541
                self::suscribe_sessions_to_hr_manager(
5542
                    $userInfo,
5543
                    $sessionList,
5544
                    $sendEmail,
5545
                    $removeOldRelationShips
5546
                );
5547
            }
5548
        }
5549
    }
5550
5551
    /**
5552
     * @param array $userSessionList format see self::importSessionDrhCSV()
5553
     *
5554
     * @return string
5555
     */
5556
    public static function checkSubscribeDrhToSessionList($userSessionList)
5557
    {
5558
        $message = null;
5559
        if (!empty($userSessionList)) {
5560
            if (!empty($userSessionList)) {
5561
                foreach ($userSessionList as $userId => $data) {
5562
                    $userInfo = $data['user_info'];
5563
5564
                    $sessionListSubscribed = self::get_sessions_followed_by_drh($userId);
5565
                    if (!empty($sessionListSubscribed)) {
5566
                        $sessionListSubscribed = array_keys($sessionListSubscribed);
5567
                    }
5568
5569
                    $sessionList = array();
5570
                    if (!empty($data['session_list'])) {
5571
                        foreach ($data['session_list'] as $sessionInfo) {
5572
                            if (in_array($sessionInfo['session_id'], $sessionListSubscribed)) {
5573
                                $sessionList[] = $sessionInfo['session_info']['name'];
5574
                            }
5575
                        }
5576
                    }
5577
5578
                    $message .= '<strong>' . get_lang('User') . '</strong> ' . $userInfo['complete_name'] . ' <br />';
5579
5580
                    if (!in_array($userInfo['status'], array(DRH)) && !api_is_platform_admin_by_id($userInfo['user_id'])) {
5581
                        $message .= get_lang('UserMustHaveTheDrhRole') . '<br />';
5582
                        continue;
5583
                    }
5584
5585
                    if (!empty($sessionList)) {
5586
                        $message .= '<strong>' . get_lang('Sessions') . ':</strong> <br />';
5587
                        $message .= implode(', ', $sessionList) . '<br /><br />';
5588
                    } else {
5589
                        $message .= get_lang('NoSessionProvided') . ' <br /><br />';
5590
                    }
5591
                }
5592
            }
5593
        }
5594
5595
        return $message;
5596
    }
5597
5598
    /**
5599
     * @param string $file
5600
     * @param bool $sendEmail
5601
     * @param bool $removeOldRelationShips
5602
     *
5603
     * @return string
5604
     */
5605
    public static function importSessionDrhCSV($file, $sendEmail, $removeOldRelationShips)
5606
    {
5607
        $list = Import::csv_reader($file);
5608
5609
        if (!empty($list)) {
5610
            $userSessionList = array();
5611
            foreach ($list as $data) {
5612
                $userInfo = api_get_user_info_from_username($data['Username']);
5613
                $sessionInfo = self::get_session_by_name($data['SessionName']);
5614
5615
                if (!empty($userInfo) && !empty($sessionInfo)) {
5616
                    $userSessionList[$userInfo['user_id']]['session_list'][] = array(
5617
                        'session_id' => $sessionInfo['id'],
5618
                        'session_info' => $sessionInfo,
5619
                    );
5620
                    $userSessionList[$userInfo['user_id']]['user_info'] = $userInfo;
5621
                }
5622
            }
5623
5624
            self::subscribeDrhToSessionList($userSessionList, $sendEmail, $removeOldRelationShips);
5625
            return self::checkSubscribeDrhToSessionList($userSessionList);
5626
        }
5627
    }
5628
5629
    /**
5630
     * Courses re-ordering in resume_session.php flag see BT#8316
5631
     */
5632
    public static function orderCourseIsEnabled()
5633
    {
5634
        $sessionCourseOrder = api_get_setting('session_course_ordering');
5635
        if ($sessionCourseOrder === 'true') {
5636
            return true;
5637
        }
5638
5639
        return false;
5640
    }
5641
5642
    /**
5643
     * @param string $direction (up/down)
5644
     * @param int $sessionId
5645
     * @param int $courseId
5646
     * @return bool
5647
     */
5648
    public static function move($direction, $sessionId, $courseId)
5649
    {
5650
        if (!self::orderCourseIsEnabled()) {
5651
            return false;
5652
        }
5653
5654
        $sessionId = intval($sessionId);
5655
        $courseId = intval($courseId);
5656
5657
        $table = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
5658
        $courseList = self::get_course_list_by_session_id($sessionId, null, 'position');
5659
5660
        $position = array();
5661
        $count = 0;
5662
        foreach ($courseList as $course) {
0 ignored issues
show
Bug introduced by
The expression $courseList of type integer|array is not guaranteed to be traversable. How about adding an additional type check?

There are different options of fixing this problem.

  1. If you want to be on the safe side, you can add an additional type-check:

    $collection = json_decode($data, true);
    if ( ! is_array($collection)) {
        throw new \RuntimeException('$collection must be an array.');
    }
    
    foreach ($collection as $item) { /** ... */ }
    
  2. If you are sure that the expression is traversable, you might want to add a doc comment cast to improve IDE auto-completion and static analysis:

    /** @var array $collection */
    $collection = json_decode($data, true);
    
    foreach ($collection as $item) { /** .. */ }
    
  3. Mark the issue as a false-positive: Just hover the remove button, in the top-right corner of this issue for more options.

Loading history...
5663
            if ($course['position'] == '') {
5664
                $course['position'] = $count;
5665
            }
5666
            $position[$course['code']] = $course['position'];
5667
            // Saving current order.
5668
            $sql = "UPDATE $table SET position = $count
5669
                    WHERE session_id = $sessionId AND c_id = '".$course['real_id']."'";
5670
            Database::query($sql);
5671
            $count++;
5672
        }
5673
5674
        // Loading new positions.
5675
        $courseList = self::get_course_list_by_session_id($sessionId, null, 'position');
5676
5677
        $found = false;
5678
5679
        switch ($direction) {
5680
            case 'up':
5681
                $courseList = array_reverse($courseList);
5682
                break;
5683
            case 'down':
5684
                break;
5685
        }
5686
5687
        foreach ($courseList as $course) {
0 ignored issues
show
Bug introduced by
The expression $courseList of type integer|array is not guaranteed to be traversable. How about adding an additional type check?

There are different options of fixing this problem.

  1. If you want to be on the safe side, you can add an additional type-check:

    $collection = json_decode($data, true);
    if ( ! is_array($collection)) {
        throw new \RuntimeException('$collection must be an array.');
    }
    
    foreach ($collection as $item) { /** ... */ }
    
  2. If you are sure that the expression is traversable, you might want to add a doc comment cast to improve IDE auto-completion and static analysis:

    /** @var array $collection */
    $collection = json_decode($data, true);
    
    foreach ($collection as $item) { /** .. */ }
    
  3. Mark the issue as a false-positive: Just hover the remove button, in the top-right corner of this issue for more options.

Loading history...
5688
            if ($found) {
5689
                $nextId = $course['real_id'];
5690
                $nextOrder = $course['position'];
5691
                break;
5692
            }
5693
5694
            if ($courseId == $course['real_id']) {
5695
                $thisCourseCode = $course['real_id'];
5696
                $thisOrder = $course['position'];
5697
                $found = true;
5698
            }
5699
        }
5700
5701
        $sql1 = "UPDATE $table SET position = '".intval($nextOrder)."'
5702
                 WHERE session_id = $sessionId AND c_id =  $thisCourseCode";
5703
        Database::query($sql1);
5704
5705
        $sql2 = "UPDATE $table SET position = '".intval($thisOrder)."'
5706
                 WHERE session_id = $sessionId AND c_id = $nextId";
5707
        Database::query($sql2);
5708
5709
        return true;
5710
    }
5711
5712
    /**
5713
     * @param int $sessionId
5714
     * @param int $courseId
5715
     * @return bool
5716
     */
5717
    public static function moveUp($sessionId, $courseId)
5718
    {
5719
        return self::move('up', $sessionId, $courseId);
5720
    }
5721
5722
    /**
5723
     * @param int $sessionId
5724
     * @param string $courseCode
5725
     * @return bool
5726
     */
5727
    public static function moveDown($sessionId, $courseCode)
5728
    {
5729
        return self::move('down', $sessionId, $courseCode);
5730
    }
5731
5732
    /**
5733
     * Use the session duration to allow/block user access see BT#8317
5734
     * Needs these DB changes
5735
     * ALTER TABLE session ADD COLUMN duration int;
5736
     * ALTER TABLE session_rel_user ADD COLUMN duration int;
5737
     */
5738
    public static function durationPerUserIsEnabled()
5739
    {
5740
        return api_get_configuration_value('session_duration_feature');
5741
    }
5742
5743
    /**
5744
     * Returns the number of days the student has left in a session when using
5745
     * sessions durations
5746
     * @param int $userId
5747
     * @param int $sessionId
5748
     * @param int $duration in days
5749
     * @return int
5750
     */
5751
    public static function getDayLeftInSession($sessionId, $userId, $duration)
5752
    {
5753
        // Get an array with the details of the first access of the student to
5754
        // this session
5755
        $courseAccess = CourseManager::getFirstCourseAccessPerSessionAndUser(
5756
            $sessionId,
5757
            $userId
5758
        );
5759
5760
        $currentTime = time();
5761
5762
        // If no previous access, return false
5763
        if (count($courseAccess) == 0) {
5764
            return false;
5765
        }
5766
5767
        $firstAccess = api_strtotime($courseAccess['login_course_date'], 'UTC');
5768
5769
        $endDateInSeconds = $firstAccess + $duration*24*60*60;
5770
        $leftDays = round(($endDateInSeconds- $currentTime) / 60 / 60 / 24);
5771
5772
        return $leftDays;
5773
    }
5774
5775
    /**
5776
     * @param int $duration
5777
     * @param int $userId
5778
     * @param int $sessionId
5779
     */
5780
    public static function editUserSessionDuration($duration, $userId, $sessionId)
5781
    {
5782
        $duration = intval($duration);
5783
        $userId = intval($userId);
5784
        $sessionId = intval($sessionId);
5785
5786
        if (empty($userId) || empty($sessionId)) {
5787
            return false;
5788
        }
5789
5790
        $table = Database::get_main_table(TABLE_MAIN_SESSION_USER);
5791
        $parameters = array('duration' => $duration);
5792
        $where = array('session_id = ? AND user_id = ? ' => array($sessionId, $userId));
5793
        Database::update($table, $parameters, $where);
5794
    }
5795
5796
    /**
5797
     * Gets one row from the session_rel_user table
5798
     * @param int $userId
5799
     * @param int $sessionId
5800
     *
5801
     * @return array
5802
     */
5803
    public static function getUserSession($userId, $sessionId)
5804
    {
5805
        $userId = intval($userId);
5806
        $sessionId = intval($sessionId);
5807
5808
        if (empty($userId) || empty($sessionId)) {
5809
            return false;
5810
        }
5811
5812
        $table = Database::get_main_table(TABLE_MAIN_SESSION_USER);
5813
        $sql = "SELECT * FROM $table
5814
                WHERE session_id = $sessionId AND user_id = $userId";
5815
        $result = Database::query($sql);
5816
        $values = array();
5817
        if (Database::num_rows($result)) {
5818
            $values = Database::fetch_array($result, 'ASSOC');
5819
        }
5820
5821
        return $values;
5822
    }
5823
5824
    /**
5825
     * Check if user is subscribed inside a session as student
5826
     * @param int $sessionId The session id
5827
     * @param int $userId The user id
5828
     * @return boolean Whether is subscribed
5829
     */
5830
    public static function isUserSubscribedAsStudent($sessionId, $userId)
5831
    {
5832
        $sessionRelUserTable = Database::get_main_table(TABLE_MAIN_SESSION_USER);
5833
5834
        $sessionId = intval($sessionId);
5835
        $userId = intval($userId);
5836
5837
        // COUNT(1) actually returns the number of rows from the table (as if
5838
        // counting the results from the first column)
5839
        $sql = "SELECT COUNT(1) AS qty FROM $sessionRelUserTable
5840
                WHERE
5841
                    session_id = $sessionId AND
5842
                    user_id = $userId AND
5843
                    relation_type = 0";
5844
5845
        $result = Database::fetch_assoc(Database::query($sql));
0 ignored issues
show
Bug introduced by
It seems like \Database::query($sql) can be null; however, fetch_assoc() does not accept null, maybe add an additional type check?

Unless you are absolutely sure that the expression can never be null because of other conditions, we strongly recommend to add an additional type check to your code:

/** @return stdClass|null */
function mayReturnNull() { }

function doesNotAcceptNull(stdClass $x) { }

// With potential error.
function withoutCheck() {
    $x = mayReturnNull();
    doesNotAcceptNull($x); // Potential error here.
}

// Safe - Alternative 1
function withCheck1() {
    $x = mayReturnNull();
    if ( ! $x instanceof stdClass) {
        throw new \LogicException('$x must be defined.');
    }
    doesNotAcceptNull($x);
}

// Safe - Alternative 2
function withCheck2() {
    $x = mayReturnNull();
    if ($x instanceof stdClass) {
        doesNotAcceptNull($x);
    }
}
Loading history...
5846
5847
        if (!empty($result) && $result['qty'] > 0) {
5848
            return true;
5849
        }
5850
5851
        return false;
5852
    }
5853
5854
    /**
5855
     * Get the session coached by a user (general coach and course-session coach)
5856
     * @param int $coachId The coach id
5857
     * @param boolean $checkSessionRelUserVisibility Check the session visibility
5858
     * @param boolean $asPlatformAdmin The user is a platform admin and we want all sessions
5859
     * @return array The session list
5860
     */
5861
    public static function getSessionsCoachedByUser($coachId, $checkSessionRelUserVisibility = false, $asPlatformAdmin = false)
5862
    {
5863
        // Get all sessions where $coachId is the general coach
5864
        $sessions = self::get_sessions_by_general_coach($coachId, $asPlatformAdmin);
5865
        // Get all sessions where $coachId is the course - session coach
5866
        $courseSessionList = self::getCoursesListByCourseCoach($coachId);
5867
        $sessionsByCoach = array();
5868
        if (!empty($courseSessionList)) {
5869
            foreach ($courseSessionList as $userCourseSubscription) {
5870
                $session = $userCourseSubscription->getSession();
5871
                $sessionsByCoach[$session->getId()] = api_get_session_info(
5872
                    $session->getId()
5873
                );
5874
            }
5875
        }
5876
5877
        if (!empty($sessionsByCoach)) {
5878
            $sessions = array_merge($sessions, $sessionsByCoach);
5879
        }
5880
5881
        // Remove repeated sessions
5882
        if (!empty($sessions)) {
5883
            $cleanSessions = array();
5884
            foreach ($sessions as $session) {
5885
                $cleanSessions[$session['id']] = $session;
5886
            }
5887
            $sessions = $cleanSessions;
5888
        }
5889
5890
        if ($checkSessionRelUserVisibility) {
5891
            if (!empty($sessions)) {
5892
                $newSessions = array();
5893
                foreach ($sessions as $session) {
5894
                    $visibility = api_get_session_visibility($session['id']);
5895
                    if ($visibility == SESSION_INVISIBLE) {
5896
                        continue;
5897
                    }
5898
                    $newSessions[] = $session;
5899
                }
5900
                $sessions = $newSessions;
5901
            }
5902
        }
5903
5904
        return $sessions;
5905
    }
5906
5907
    /**
5908
     * Check if the course belongs to the session
5909
     * @param int $sessionId The session id
5910
     * @param string $courseCode The course code
5911
     *
5912
     * @return bool
5913
     */
5914
    public static function sessionHasCourse($sessionId, $courseCode)
5915
    {
5916
        $sessionId = intval($sessionId);
5917
        $courseCode = Database::escape_string($courseCode);
5918
5919
        $courseTable = Database::get_main_table(TABLE_MAIN_COURSE);
5920
        $sessionRelCourseTable = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
5921
5922
        $sql = "SELECT COUNT(1) AS qty
5923
                FROM $courseTable c
5924
                INNER JOIN $sessionRelCourseTable src
5925
                ON c.id = src.c_id
5926
                WHERE src.session_id = $sessionId
5927
                AND c.code = '$courseCode'  ";
5928
5929
        $result = Database::query($sql);
5930
5931
        if ($result !== false) {
5932
            $data = Database::fetch_assoc($result);
5933
5934
            if ($data['qty'] > 0) {
5935
                return true;
5936
            }
5937
        }
5938
5939
        return false;
5940
    }
5941
5942
    /**
5943
     * Get the list of course coaches
5944
     * @return array The list
5945
     */
5946
    public static function getAllCourseCoaches()
5947
    {
5948
        $coaches = array();
5949
5950
        $scuTable = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
5951
        $userTable = Database::get_main_table(TABLE_MAIN_USER);
5952
5953
        $idResult = Database::select('DISTINCT user_id', $scuTable, array(
5954
            'where' => array(
5955
                'status = ?' => 2,
5956
            ),
5957
        ));
5958
5959
        if ($idResult != false) {
5960
            foreach ($idResult as $idData) {
5961
                $userResult = Database::select('user_id, lastname, firstname, username', $userTable, array(
5962
                    'where' => array(
5963
                        'user_id = ?' => $idData['user_id'],
5964
                    ),
5965
                ), 'first');
5966
5967
                if ($userResult != false) {
5968
                    $coaches[] = array(
5969
                        'id' => $userResult['user_id'],
5970
                        'lastname' => $userResult['lastname'],
5971
                        'firstname' => $userResult['firstname'],
5972
                        'username' => $userResult['username'],
5973
                        'completeName' => api_get_person_name(
5974
                            $userResult['firstname'],
5975
                            $userResult['lastname']
5976
                        ),
5977
                    );
5978
                }
5979
            }
5980
        }
5981
5982
        return $coaches;
5983
    }
5984
5985
    /**
5986
     * Calculate the total user time in the platform
5987
     * @param int $userId The user id
5988
     * @param string $from Optional. From date
5989
     * @param string $until Optional. Until date
5990
     * @return string The time (hh:mm:ss)
5991
     */
5992
    public static function getTotalUserTimeInPlatform($userId, $from = '', $until = '')
5993
    {
5994
        $userId = intval($userId);
5995
5996
        $trackLoginTable = Database::get_main_table(TABLE_STATISTIC_TRACK_E_LOGIN);
5997
5998
        $whereConditions = array(
5999
            'login_user_id = ? ' => $userId,
6000
        );
6001
6002 View Code Duplication
        if (!empty($from) && !empty($until)) {
6003
            $whereConditions["AND (login_date >= '?' "] = $from;
6004
            $whereConditions["AND logout_date <= DATE_ADD('?', INTERVAL 1 DAY)) "] = $until;
6005
        }
6006
6007
        $trackResult = Database::select(
6008
            'SEC_TO_TIME(SUM(UNIX_TIMESTAMP(logout_date) - UNIX_TIMESTAMP(login_date))) as total_time',
6009
            $trackLoginTable,
6010
            array(
6011
                'where' => $whereConditions,
6012
            ), 'first'
6013
        );
6014
6015
        if ($trackResult != false) {
6016
            return $trackResult['total_time'] ? $trackResult['total_time'] : '00:00:00';
6017
        }
6018
6019
        return '00:00:00';
6020
    }
6021
6022
    /**
6023
     * Get the courses list by a course coach
6024
     * @param int $coachId The coach id
6025
     * @return array (id, user_id, session_id, c_id, visibility, status, legal_agreement)
6026
     */
6027
    public static function getCoursesListByCourseCoach($coachId)
6028
    {
6029
        $entityManager = Database::getManager();
6030
        $scuRepo = $entityManager->getRepository(
6031
            'ChamiloCoreBundle:SessionRelCourseRelUser'
6032
        );
6033
6034
        return $scuRepo->findBy([
6035
            'user' => $coachId,
6036
            'status' => SessionRelCourseRelUser::STATUS_COURSE_COACH
6037
        ]);
6038
    }
6039
6040
	/**
6041
     * Get the count of user courses in session
6042
     * @param int $sessionId The session id
6043
     * @return array
6044
     */
6045
    public static function getTotalUserCoursesInSession($sessionId)
6046
    {
6047
        $tableUser = Database::get_main_table(TABLE_MAIN_USER);
6048
        $tableSessionRelCourseRelUser = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
6049
        $sql = "SELECT COUNT(1) as count, u.id, scu.status status_in_session, u.status user_status
6050
                FROM $tableSessionRelCourseRelUser scu
6051
                INNER JOIN $tableUser u ON scu.user_id = u.id
6052
                WHERE scu.session_id = " . intval($sessionId) ."
6053
                GROUP BY u.id";
6054
6055
        $result = Database::query($sql);
6056
6057
        $list = array();
6058
        while ($data = Database::fetch_assoc($result)) {
6059
            $list[] = $data;
6060
        }
6061
6062
        return $list;
6063
    }
6064
6065
6066
    /**
6067
     * Returns list of a few data from session (name, short description, start
6068
     * date, end date) and the given extra fields if defined based on a
6069
     * session category Id.
6070
     * @param int $categoryId The internal ID of the session category
6071
     * @param string $target Value to search for in the session field values
6072
     * @param array $extraFields A list of fields to be scanned and returned
6073
     * @return mixed
6074
     */
6075
    public static function getShortSessionListAndExtraByCategory($categoryId, $target, $extraFields = null, $publicationDate = null)
6076
    {
6077
        // Init variables
6078
        $categoryId = (int) $categoryId;
6079
        $sessionList = array();
6080
        // Check if categoryId is valid
6081
        if ($categoryId > 0) {
6082
            $target = Database::escape_string($target);
6083
            $sTable = Database::get_main_table(TABLE_MAIN_SESSION);
6084
            $sfTable = Database::get_main_table(TABLE_EXTRA_FIELD);
6085
            $sfvTable = Database::get_main_table(TABLE_EXTRA_FIELD_VALUES);
6086
            // Join session field and session field values tables
6087
            $joinTable = $sfTable . ' sf INNER JOIN ' . $sfvTable . ' sfv ON sf.id = sfv.field_id';
6088
            $fieldsArray = array();
6089
            foreach ($extraFields as $field) {
0 ignored issues
show
Bug introduced by
The expression $extraFields of type array|null is not guaranteed to be traversable. How about adding an additional type check?

There are different options of fixing this problem.

  1. If you want to be on the safe side, you can add an additional type-check:

    $collection = json_decode($data, true);
    if ( ! is_array($collection)) {
        throw new \RuntimeException('$collection must be an array.');
    }
    
    foreach ($collection as $item) { /** ... */ }
    
  2. If you are sure that the expression is traversable, you might want to add a doc comment cast to improve IDE auto-completion and static analysis:

    /** @var array $collection */
    $collection = json_decode($data, true);
    
    foreach ($collection as $item) { /** .. */ }
    
  3. Mark the issue as a false-positive: Just hover the remove button, in the top-right corner of this issue for more options.

Loading history...
6090
                $fieldsArray[] = Database::escape_string($field);
6091
            }
6092
            $extraFieldType = \Chamilo\CoreBundle\Entity\ExtraField::SESSION_FIELD_TYPE;
6093
            if (isset ($publicationDate)) {
6094
                $publicationDateString = $publicationDate->format('Y-m-d H:i:s');
6095
                $wherePublication = " AND id NOT IN (
6096
                    SELECT sfv.item_id FROM $joinTable
6097
                    WHERE
6098
                        sf.extra_field_type = $extraFieldType AND
6099
                        ((sf.variable = 'publication_start_date' AND sfv.value > '$publicationDateString' and sfv.value != '') OR
6100
                        (sf.variable = 'publication_end_date' AND sfv.value < '$publicationDateString' and sfv.value != ''))
6101
                )";
6102
            }
6103
            // Get the session list from session category and target
6104
            $sessionList = Database::select(
6105
                'id, name, access_start_date, access_end_date',
6106
                $sTable,
6107
                array(
6108
                    'where' => array(
6109
                        "session_category_id = ? AND id IN (
6110
                            SELECT sfv.item_id FROM $joinTable
6111
                            WHERE
6112
                                sf.extra_field_type = $extraFieldType AND
6113
                                sfv.item_id = session.id AND
6114
                                sf.variable = 'target' AND
6115
                                sfv.value = ?
6116
                        ) $wherePublication" => array($categoryId, $target),
6117
                    ),
6118
                )
6119
            );
6120
            $whereFieldVariables = array();
6121
            $whereFieldIds = array();
6122
            if (
6123
                is_array($fieldsArray) &&
6124
                count($fieldsArray) > 0
6125
            ) {
6126
                $whereParams = '?';
6127
                for ($i = 1; $i < count($fieldsArray); $i++) {
6128
                    $whereParams .= ', ?';
6129
                }
6130
                $whereFieldVariables = ' variable IN ( ' . $whereParams .' )';
6131
                $whereFieldIds = 'field_id IN ( ' . $whereParams .  ' )';
6132
            }
6133
            // Get session fields
6134
            $extraField = new ExtraField('session');
6135
            $questionMarks = substr(str_repeat('?, ', count($fieldsArray)), 0, -2);
6136
            $fieldsList = $extraField->get_all(array(
6137
                ' variable IN ( ' . $questionMarks . ' )' => $fieldsArray,
6138
            ));
6139
            // Index session fields
6140
            foreach ($fieldsList as $field) {
6141
                $fields[$field['id']] = $field['variable'];
6142
            }
6143
            // Get session field values
6144
            $extra = new ExtraFieldValue('session');
6145
            $questionMarksFields = substr(str_repeat('?, ', count($fields)), 0, -2);
6146
            $sessionFieldValueList = $extra->get_all(array ('where' => array('field_id IN ( ' . $questionMarksFields . ' )' => array_keys($fields))));
6147
            // Add session fields values to session list
6148
            foreach ($sessionList as $id => &$session) {
6149
                foreach ($sessionFieldValueList as $sessionFieldValue) {
6150
                    // Match session field values to session
6151
                    if ($sessionFieldValue['item_id'] == $id) {
6152
                        // Check if session field value is set in session field list
6153
                        if (isset($fields[$sessionFieldValue['field_id']])) {
6154
                            // Avoid overwriting the session's ID field
6155
                            if ($fields[$sessionFieldValue['field_id']] != 'id') {
6156
                                $var = $fields[$sessionFieldValue['field_id']];
6157
                                $val = $sessionFieldValue['value'];
6158
                                // Assign session field value to session
6159
                                $session[$var] = $val;
6160
                            }
6161
                        }
6162
                    }
6163
                }
6164
            }
6165
        }
6166
6167
        return $sessionList;
6168
    }
6169
6170
    /**
6171
     * Return the Session Category id searched by name
6172
     * @param string $categoryName Name attribute of session category used for search query
6173
     * @param bool $force boolean used to get even if something is wrong (e.g not unique name)
6174
     * @return int|array If success, return category id (int), else it will return an array
6175
     * with the next structure:
6176
     * array('error' => true, 'errorMessage' => ERROR_MESSAGE)
6177
     */
6178
    public static function getSessionCategoryIdByName($categoryName, $force = false)
6179
    {
6180
        // Start error result
6181
        $errorResult = array('error' => true, 'errorMessage' => get_lang('ThereWasAnError'));
6182
        $categoryName = Database::escape_string($categoryName);
6183
        // Check if is not empty category name
6184
        if (!empty($categoryName)) {
6185
            $sessionCategoryTable = Database::get_main_table(TABLE_MAIN_SESSION_CATEGORY);
6186
            // Get all session category with same name
6187
            $result = Database::select(
6188
                'id',
6189
                $sessionCategoryTable,
6190
                array(
6191
                    'where' => array(
6192
                        'name = ?' => $categoryName,
6193
                    ),
6194
                )
6195
            );
6196
            // Check the result
6197
            if ($result < 1) {
6198
                // If not found any result, update error message
6199
                $errorResult['errorMessage'] = 'Not found any session category name ' . $categoryName;
6200
            } elseif (count($result) > 1 && !$force) {
6201
                // If found more than one result and force is disabled, update error message
6202
                $errorResult['errorMessage'] = 'Found many session categories';
6203
            } elseif (count($result) == 1 || $force) {
6204
                // If found just one session category or force option is enabled
6205
6206
                return key($result);
6207
            }
6208
        } else {
6209
            // category name is empty, update error message
6210
            $errorResult['errorMessage'] = 'Not valid category name';
6211
        }
6212
6213
        return $errorResult;
6214
    }
6215
6216
    /**
6217
     * Return all data from sessions (plus extra field, course and coach data) by category id
6218
     * @param int $sessionCategoryId session category id used to search sessions
6219
     * @return array If success, return session list and more session related data, else it will return an array
6220
     * with the next structure:
6221
     * array('error' => true, 'errorMessage' => ERROR_MESSAGE)
6222
     */
6223
    public static function getSessionListAndExtraByCategoryId($sessionCategoryId)
6224
    {
6225
        // Start error result
6226
        $errorResult = array(
6227
            'error' => true,
6228
            'errorMessage' => get_lang('ThereWasAnError'),
6229
        );
6230
6231
        $sessionCategoryId = intval($sessionCategoryId);
6232
        // Check if session category id is valid
6233
        if ($sessionCategoryId > 0) {
6234
            // Get table names
6235
            $sessionTable = Database::get_main_table(TABLE_MAIN_SESSION);
6236
            $sessionFieldTable = Database::get_main_table(TABLE_EXTRA_FIELD);
6237
            $sessionFieldValueTable = Database::get_main_table(TABLE_EXTRA_FIELD_VALUES);
6238
            $sessionCourseUserTable = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
6239
            $userTable = Database::get_main_table(TABLE_MAIN_USER);
6240
            $courseTable = Database::get_main_table(TABLE_MAIN_COURSE);
6241
6242
            // Get all data from all sessions whit the session category specified
6243
            $sessionList = Database::select(
6244
                '*',
6245
                $sessionTable,
6246
                array(
6247
                    'where' => array(
6248
                        'session_category_id = ?' => $sessionCategoryId,
6249
                    ),
6250
                )
6251
            );
6252
6253
            $extraFieldType = \Chamilo\CoreBundle\Entity\ExtraField::SESSION_FIELD_TYPE;
6254
6255
            // Check if session list query had result
6256
            if (!empty($sessionList)) {
6257
                // implode all session id
6258
                $sessionIdsString = '(' . implode(', ', array_keys($sessionList)) . ')';
6259
                // Get all field variables
6260
                $sessionFieldList = Database::select(
6261
                    'id, variable',
6262
                    $sessionFieldTable,
6263
                    array('extra_field_type = ? ' => array($extraFieldType))
6264
                );
6265
6266
                // Get all field values
6267
                $sql = "SELECT item_id, field_id, value FROM
6268
                        $sessionFieldValueTable v INNER JOIN $sessionFieldTable f
6269
                        ON (f.id = v.field_id)
6270
                        WHERE
6271
                            item_id IN $sessionIdsString AND
6272
                            extra_field_type = $extraFieldType
6273
                ";
6274
                $result = Database::query($sql);
6275
                $sessionFieldValueList = Database::store_result($result, 'ASSOC');
6276
6277
                // Check if session field values had result
6278
                if (!empty($sessionFieldValueList)) {
6279
                    $sessionFieldValueListBySession = array();
6280
                    foreach ($sessionFieldValueList as $key => $sessionFieldValue) {
6281
                        // Create an array to index ids to session id
6282
                        $sessionFieldValueListBySession[$sessionFieldValue['item_id']][] = $key;
6283
                    }
6284
                }
6285
                // Query used to find course-coaches from sessions
6286
                $sql = "SELECT
6287
                        scu.session_id,
6288
                        c.id AS course_id,
6289
                        c.code AS course_code,
6290
                        c.title AS course_title,
6291
                        u.username AS coach_username,
6292
                        u.firstname AS coach_firstname,
6293
                        u.lastname AS coach_lastname
6294
                        FROM $courseTable c
6295
                        INNER JOIN $sessionCourseUserTable scu ON c.id = scu.c_id
6296
                        INNER JOIN $userTable u ON scu.user_id = u.user_id
6297
                        WHERE scu.status = 2 AND scu.session_id IN $sessionIdsString
6298
                        ORDER BY scu.session_id ASC ";
6299
                $res = Database::query($sql);
6300
                $sessionCourseList = Database::store_result($res, 'ASSOC');
6301
                // Check if course list had result
6302
                if (!empty($sessionCourseList)) {
6303
                    foreach ($sessionCourseList as $key => $sessionCourse) {
6304
                        // Create an array to index ids to session_id
6305
                        $sessionCourseListBySession[$sessionCourse['session_id']][] = $key;
6306
                    }
6307
                }
6308
                // Join lists
6309
                if (is_array($sessionList)) {
6310
                    foreach ($sessionList as $id => &$row) {
6311
                        if (
6312
                            !empty($sessionFieldValueListBySession) &&
6313
                            is_array($sessionFieldValueListBySession[$id])
6314
                        ) {
6315
                            // If have an index array for session extra fields, use it to join arrays
6316
                            foreach ($sessionFieldValueListBySession[$id] as $key) {
6317
                                $row['extra'][$key] = array(
6318
                                    'field_name' => $sessionFieldList[$sessionFieldValueList[$key]['field_id']]['variable'],
6319
                                    'value' => $sessionFieldValueList[$key]['value'],
6320
                                );
6321
                            }
6322
                        }
6323
                        if (
6324
                            !empty($sessionCourseListBySession) &&
6325
                            is_array($sessionCourseListBySession[$id])
6326
                        ) {
6327
                            // If have an index array for session course coach, use it to join arrays
6328
                            foreach ($sessionCourseListBySession[$id] as $key) {
6329
                                $row['course'][$key] = array(
6330
                                    'course_id' => $sessionCourseList[$key]['course_id'],
6331
                                    'course_code' => $sessionCourseList[$key]['course_code'],
6332
                                    'course_title' => $sessionCourseList[$key]['course_title'],
6333
                                    'coach_username' => $sessionCourseList[$key]['coach_username'],
6334
                                    'coach_firstname' => $sessionCourseList[$key]['coach_firstname'],
6335
                                    'coach_lastname' => $sessionCourseList[$key]['coach_lastname'],
6336
                                );
6337
                            }
6338
                        }
6339
                    }
6340
                }
6341
6342
                return $sessionList;
6343
            } else {
6344
                // Not found result, update error message
6345
                $errorResult['errorMessage'] = 'Not found any session for session category id ' . $sessionCategoryId;
6346
            }
6347
        }
6348
6349
        return $errorResult;
6350
    }
6351
6352
    /**
6353
     * Return session description from session id
6354
     * @param int $sessionId
6355
     * @return string
6356
     */
6357
    public static function getDescriptionFromSessionId($sessionId)
6358
    {
6359
        // Init variables
6360
        $sessionId = intval($sessionId);
6361
        $description = '';
6362
        // Check if session id is valid
6363
        if ($sessionId > 0) {
6364
            // Select query from session id
6365
            $rows = Database::select(
6366
                'description',
6367
                Database::get_main_table(TABLE_MAIN_SESSION),
6368
                array(
6369
                    'where' => array(
6370
                        'id = ?' => $sessionId,
6371
                    ),
6372
                )
6373
            );
6374
6375
            // Check if select query result is not empty
6376
            if (!empty($rows)) {
6377
                // Get session description
6378
                $description = $rows[0]['description'];
6379
            }
6380
        }
6381
6382
        return $description;
6383
    }
6384
6385
    /**
6386
     * Get a session list filtered by name, description or any of the given extra fields
6387
     * @param string $term The term to search
6388
     * @param array $extraFieldsToInclude Extra fields to include in the session data
6389
     * @return array The list
6390
     */
6391
    public static function searchSession($term, $extraFieldsToInclude = array())
6392
    {
6393
        $sTable = Database::get_main_table(TABLE_MAIN_SESSION);
6394
        $extraFieldTable = Database::get_main_table(TABLE_EXTRA_FIELD);
6395
        $sfvTable = Database::get_main_table(TABLE_EXTRA_FIELD_VALUES);
6396
6397
        $term = Database::escape_string($term);
6398
        $extraFieldType = \Chamilo\CoreBundle\Entity\ExtraField::SESSION_FIELD_TYPE;
6399
        if (is_array($extraFieldsToInclude) && count($extraFieldsToInclude) > 0) {
6400
            $resultData = Database::select('*', $sTable, array(
6401
                'where' => array(
6402
                    "name LIKE %?% " => $term,
6403
                    " OR description LIKE %?% " => $term,
6404
                    " OR id IN (
6405
                    SELECT item_id
6406
                    FROM $sfvTable v INNER JOIN $extraFieldTable e
6407
                    ON (v.field_id = e.id)
6408
                    WHERE value LIKE %?% AND extra_field_type = $extraFieldType
6409
                ) " => $term,
6410
                ),
6411
            ));
6412
        } else {
6413
            $resultData = Database::select('*', $sTable, array(
6414
                'where' => array(
6415
                    "name LIKE %?% " => $term,
6416
                    "OR description LIKE %?% " => $term,
6417
                ),
6418
            ));
6419
6420
            return $resultData;
6421
        }
6422
6423
        foreach ($resultData as $id => &$session) {
6424
            $session['extra'] = self::getFilteredExtraFields($id, $extraFieldsToInclude);
6425
        }
6426
6427
        return $resultData;
6428
    }
6429
6430
    /**
6431
     * @param $sessionId
6432
     * @param array $extraFieldsToInclude
6433
     * @return array
6434
     */
6435
    public static function getFilteredExtraFields($sessionId, $extraFieldsToInclude = array())
6436
    {
6437
        $extraData = array();
6438
6439
        $variables = array();
6440
        $variablePlaceHolders = array();
6441
6442
        foreach ($extraFieldsToInclude as $sessionExtraField) {
6443
            $variablePlaceHolders[] = "?";
6444
            $variables[] = Database::escape_string($sessionExtraField);
6445
        }
6446
6447
        $sessionExtraField = new ExtraField('session');
6448
        $fieldList = $sessionExtraField->get_all(array(
6449
            "variable IN ( " . implode(", ", $variablePlaceHolders) . " ) " => $variables,
6450
        ));
6451
6452
        $fields = array();
6453
6454
        // Index session fields
6455
        foreach ($fieldList as $field) {
6456
            $fields[$field['id']] = $field['variable'];
6457
        }
6458
6459
        // Get session field values
6460
        $extra = new ExtraFieldValue('session');
6461
        $sessionFieldValueList = $extra->get_all(
6462
            array(
6463
                "field_id IN ( " . implode(", ", $variablePlaceHolders) . " )" => array_keys($fields),
6464
            )
6465
        );
6466
6467
        foreach ($sessionFieldValueList as $sessionFieldValue) {
6468
            // Match session field values to session
6469
            if ($sessionFieldValue['item_id'] != $sessionId) {
6470
                continue;
6471
            }
6472
6473
            // Check if session field value is set in session field list
6474
            if (!isset($fields[$sessionFieldValue['field_id']])) {
6475
                continue;
6476
            }
6477
6478
            $extrafieldVariable = $fields[$sessionFieldValue['field_id']];
6479
            $extrafieldValue = $sessionFieldValue['value'];
6480
6481
            $extraData[] = array(
6482
                'variable' => $extrafieldVariable,
6483
                'value' => $extrafieldValue,
6484
            );
6485
        }
6486
6487
        return $extraData;
6488
    }
6489
6490
    /**
6491
     * @param int $sessionId
6492
     *
6493
     * @return bool
6494
     */
6495
    public static function isValidId($sessionId)
6496
    {
6497
        $sessionId = intval($sessionId);
6498
        if ($sessionId > 0) {
6499
            $rows = Database::select(
6500
                'id',
6501
                Database::get_main_table(TABLE_MAIN_SESSION),
6502
                array('where' => array('id = ?' => $sessionId))
6503
            );
6504
            if (!empty($rows)) {
6505
6506
                return true;
6507
            }
6508
        }
6509
6510
        return false;
6511
    }
6512
6513
    /**
6514
     * Get list of sessions based on users of a group for a group admin
6515
     * @param int $userId The user id
6516
     * @return array
6517
     */
6518 View Code Duplication
    public static function getSessionsFollowedForGroupAdmin($userId)
6519
    {
6520
        $sessionList = array();
6521
        $sessionTable = Database::get_main_table(TABLE_MAIN_SESSION);
6522
        $sessionUserTable = Database::get_main_table(TABLE_MAIN_SESSION_USER);
6523
        $userGroup = new UserGroup();
6524
        $userIdList = $userGroup->getGroupUsersByUser($userId);
6525
6526
        if (empty($userIdList)) {
6527
            return [];
6528
        }
6529
6530
        $sql = "SELECT DISTINCT s.*
6531
                FROM $sessionTable s
6532
                INNER JOIN $sessionUserTable sru ON s.id = sru.id_session
6533
                WHERE
6534
                    (sru.id_user IN (" . implode(', ', $userIdList) . ")
6535
                    AND sru.relation_type = 0
6536
                )";
6537
6538
        if (api_is_multiple_url_enabled()) {
6539
            $sessionAccessUrlTable = Database::get_main_table(TABLE_MAIN_ACCESS_URL_REL_SESSION);
6540
            $accessUrlId = api_get_current_access_url_id();
6541
6542
            if ($accessUrlId != -1) {
6543
                $sql = "SELECT DISTINCT s.*
6544
                        FROM $sessionTable s
6545
                        INNER JOIN $sessionUserTable sru ON s.id = sru.id_session
6546
                        INNER JOIN $sessionAccessUrlTable srau ON s.id = srau.session_id
6547
                        WHERE
6548
                            srau.access_url_id = $accessUrlId
6549
                            AND (
6550
                                sru.id_user IN (" . implode(', ', $userIdList) . ")
6551
                                AND sru.relation_type = 0
6552
                            )";
6553
            }
6554
        }
6555
6556
        $result = Database::query($sql);
6557
6558
        while ($row = Database::fetch_assoc($result)) {
6559
            $sessionList[] = $row;
6560
        }
6561
6562
        return $sessionList;
6563
    }
6564
6565
    /**
6566
     * @param array $sessionInfo
6567
     * @return string
6568
     */
6569
    public static function getSessionVisibility($sessionInfo)
6570
    {
6571
        switch($sessionInfo['visibility']) {
6572
            case 1:
6573
                return get_lang('ReadOnly');
6574
            case 2:
6575
               return get_lang('Visible');
6576
            case 3:
6577
                return api_ucfirst(get_lang('Invisible'));
6578
        }
6579
    }
6580
6581
    /**
6582
     * Converts "start date" and "end date" to "From start date to end date" string
6583
     * @param string $startDate
6584
     * @param string $endDate
6585
     *
6586
     * @return string
6587
     */
6588
    private static function convertSessionDateToString($startDate, $endDate)
6589
    {
6590
        $startDateToLocal = '';
6591
        $endDateToLocal = '';
6592
        // This will clean the variables if 0000-00-00 00:00:00 the variable will be empty
6593
        if (isset($startDateToLocal)) {
6594
            $startDateToLocal = api_get_local_time($startDate, null, null, true);
6595
        }
6596
        if (isset($endDateToLocal)) {
6597
            $endDateToLocal = api_get_local_time($endDate, null, null, true);
6598
        }
6599
6600
        $result = '';
6601
        if (!empty($startDateToLocal) && !empty($endDateToLocal)) {
6602
            $result =  sprintf(get_lang('FromDateXToDateY'), $startDateToLocal, $endDateToLocal);
6603
        } else {
6604
            if (!empty($startDateToLocal)) {
6605
                $result = get_lang('From').' '.$startDateToLocal;
6606
            }
6607
            if (!empty($endDateToLocal)) {
6608
                $result = get_lang('Until').' '.$endDateToLocal;
6609
            }
6610
        }
6611
6612
        if (empty($result)) {
6613
            $result = get_lang('NoTimeLimits');
6614
        }
6615
6616
        return $result;
6617
    }
6618
6619
    /**
6620
     * Returns a human readable string
6621
     * @params array $sessionInfo An array with all the session dates
6622
     * @return string
6623
     */
6624
    public static function parseSessionDates($sessionInfo)
6625
    {
6626
        $displayDates = self::convertSessionDateToString(
6627
            $sessionInfo['display_start_date'],
6628
            $sessionInfo['display_end_date']
6629
        );
6630
6631
        $accessDates = self::convertSessionDateToString(
6632
            $sessionInfo['access_start_date'],
6633
            $sessionInfo['access_end_date']
6634
        );
6635
6636
        $coachDates = self::convertSessionDateToString(
6637
            $sessionInfo['coach_access_start_date'],
6638
            $sessionInfo['coach_access_end_date']
6639
        );
6640
6641
        $result = [
6642
            'access' => $accessDates,
6643
            'display' => $displayDates,
6644
            'coach' => $coachDates,
6645
        ];
6646
6647
        return $result;
6648
    }
6649
6650
    /**
6651
     * @param FormValidator $form
6652
     *
6653
     * @return array
6654
     */
6655
    public static function setForm(FormValidator & $form, $sessionId = 0)
6656
    {
6657
        $categoriesList = SessionManager::get_all_session_category();
6658
        $userInfo = api_get_user_info();
6659
6660
        $categoriesOptions = array(
6661
            '0' => get_lang('None'),
6662
        );
6663
6664
        if ($categoriesList != false) {
6665
            foreach ($categoriesList as $categoryItem) {
6666
                $categoriesOptions[$categoryItem['id']] = $categoryItem['name'];
6667
            }
6668
        }
6669
6670
        // Database Table Definitions
6671
        $tbl_user = Database::get_main_table(TABLE_MAIN_USER);
6672
6673
        $form->addElement('text', 'name', get_lang('SessionName'), array(
6674
            'maxlength' => 50,
6675
        ));
6676
        $form->addRule('name', get_lang('ThisFieldIsRequired'), 'required');
6677
        $form->addRule('name', get_lang('SessionNameAlreadyExists'), 'callback', 'check_session_name');
6678
6679
        if (!api_is_platform_admin() && api_is_teacher()) {
6680
            $form->addElement(
6681
                'select',
6682
                'coach_username',
6683
                get_lang('CoachName'),
6684
                [api_get_user_id() => $userInfo['complete_name']],
6685
                array(
6686
                    'id' => 'coach_username',
6687
                    'style' => 'width:370px;',
6688
                )
6689
            );
6690
        } else {
6691
6692
            $sql = "SELECT COUNT(1) FROM $tbl_user WHERE status = 1";
6693
            $rs = Database::query($sql);
6694
            $countUsers = Database::result($rs, 0, 0);
6695
6696
            if (intval($countUsers) < 50) {
6697
                $orderClause = "ORDER BY ";
6698
                $orderClause .= api_sort_by_first_name() ? "firstname, lastname, username" : "lastname, firstname, username";
6699
6700
                $sql = "SELECT user_id, lastname, firstname, username
6701
                        FROM $tbl_user
6702
                        WHERE status = '1' ".
6703
                        $orderClause;
6704
6705 View Code Duplication
                if (api_is_multiple_url_enabled()) {
6706
                    $userRelAccessUrlTable = Database::get_main_table(
6707
                        TABLE_MAIN_ACCESS_URL_REL_USER
6708
                    );
6709
                    $accessUrlId = api_get_current_access_url_id();
6710
6711
                    if ($accessUrlId != -1) {
6712
                        $sql = "SELECT user.user_id, username, lastname, firstname
6713
                        FROM $tbl_user user
6714
                        INNER JOIN $userRelAccessUrlTable url_user
6715
                        ON (url_user.user_id = user.user_id)
6716
                        WHERE
6717
                            access_url_id = $accessUrlId AND
6718
                            status = 1 "
6719
                            .$orderClause;
6720
                    }
6721
                }
6722
6723
                $result = Database::query($sql);
6724
                $coachesList = Database::store_result($result);
6725
6726
                $coachesOptions = array();
6727 View Code Duplication
                foreach ($coachesList as $coachItem) {
6728
                    $coachesOptions[$coachItem['user_id']] =
6729
                        api_get_person_name($coachItem['firstname'], $coachItem['lastname']).' ('.$coachItem['username'].')';
6730
                }
6731
6732
                $form->addElement(
6733
                    'select',
6734
                    'coach_username',
6735
                    get_lang('CoachName'),
6736
                    $coachesOptions
6737
                );
6738
            } else {
6739
                $form->addElement(
6740
                    'select_ajax',
6741
                    'coach_username',
6742
                    get_lang('CoachName'),
6743
                    null,
6744
                    [
6745
                        'url' => api_get_path(WEB_AJAX_PATH) . 'session.ajax.php?a=search_general_coach',
6746
                        'width' => '100%',
6747
                    ]
6748
                );
6749
            }
6750
        }
6751
6752
        $form->addRule('coach_username', get_lang('ThisFieldIsRequired'), 'required');
6753
        $form->addHtml('<div id="ajax_list_coachs"></div>');
6754
6755
        $form->addButtonAdvancedSettings('advanced_params');
6756
        $form->addElement('html','<div id="advanced_params_options" style="display:none">');
6757
6758
        $form->addSelect('session_category', get_lang('SessionCategory'), $categoriesOptions, array(
6759
            'id' => 'session_category'
6760
        ));
6761
6762
        $form->addHtmlEditor(
6763
            'description',
6764
            get_lang('Description'),
6765
            false,
6766
            false,
6767
            array(
6768
                'ToolbarSet' => 'Minimal',
6769
            )
6770
        );
6771
6772
        $form->addElement('checkbox', 'show_description', null, get_lang('ShowDescription'));
6773
6774
        $visibilityGroup = array();
6775
        $visibilityGroup[] = $form->createElement('select', 'session_visibility', null, array(
6776
            SESSION_VISIBLE_READ_ONLY => get_lang('SessionReadOnly'),
6777
            SESSION_VISIBLE => get_lang('SessionAccessible'),
6778
            SESSION_INVISIBLE => api_ucfirst(get_lang('SessionNotAccessible')),
6779
        ));
6780
        $form->addGroup($visibilityGroup, 'visibility_group', get_lang('SessionVisibility'), null, false);
6781
6782
        $options = [
6783
            0 => get_lang('ByDuration'),
6784
            1 => get_lang('ByDates'),
6785
        ];
6786
6787
        $form->addSelect('access', get_lang('Access'), $options, array(
6788
            'onchange' => 'accessSwitcher()',
6789
            'id' => 'access',
6790
        ));
6791
6792
        $form->addElement('html', '<div id="duration" style="display:none">');
6793
6794
        $form->addElement(
6795
            'number',
6796
            'duration',
6797
            array(
6798
                get_lang('SessionDurationTitle'),
6799
                get_lang('SessionDurationDescription'),
6800
            ),
6801
            array(
6802
                'maxlength' => 50,
6803
            )
6804
        );
6805
6806
        $form->addElement('html', '</div>');
6807
6808
        $form->addElement('html', '<div id="date_fields" style="display:none">');
6809
6810
        // Dates
6811
6812
        $form->addDateTimePicker(
6813
            'access_start_date',
6814
            array(get_lang('SessionStartDate'), get_lang('SessionStartDateComment')),
6815
            array('id' => 'access_start_date')
6816
        );
6817
6818
        $form->addDateTimePicker(
6819
            'access_end_date',
6820
            array(get_lang('SessionEndDate'), get_lang('SessionEndDateComment')),
6821
            array('id' => 'access_end_date')
6822
        );
6823
6824
        $form->addRule(
6825
            array('access_start_date', 'access_end_date'),
6826
            get_lang('StartDateMustBeBeforeTheEndDate'),
6827
            'compare_datetime_text',
6828
            '< allow_empty'
6829
        );
6830
6831
        $form->addDateTimePicker(
6832
            'display_start_date',
6833
            array(
6834
                get_lang('SessionDisplayStartDate'),
6835
                get_lang('SessionDisplayStartDateComment'),
6836
            ),
6837
            array('id' => 'display_start_date')
6838
        );
6839
        $form->addDateTimePicker(
6840
            'display_end_date',
6841
            array(
6842
                get_lang('SessionDisplayEndDate'),
6843
                get_lang('SessionDisplayEndDateComment'),
6844
            ),
6845
            array('id' => 'display_end_date')
6846
        );
6847
6848
        $form->addRule(
6849
            array('display_start_date', 'display_end_date'),
6850
            get_lang('StartDateMustBeBeforeTheEndDate'),
6851
            'compare_datetime_text',
6852
            '< allow_empty'
6853
        );
6854
6855
        $form->addDateTimePicker(
6856
            'coach_access_start_date',
6857
            array(
6858
                get_lang('SessionCoachStartDate'),
6859
                get_lang('SessionCoachStartDateComment'),
6860
            ),
6861
            array('id' => 'coach_access_start_date')
6862
        );
6863
6864
        $form->addDateTimePicker(
6865
            'coach_access_end_date',
6866
            array(
6867
                get_lang('SessionCoachEndDate'),
6868
                get_lang('SessionCoachEndDateComment'),
6869
            ),
6870
            array('id' => 'coach_access_end_date')
6871
        );
6872
6873
        $form->addRule(
6874
            array('coach_access_start_date', 'coach_access_end_date'),
6875
            get_lang('StartDateMustBeBeforeTheEndDate'),
6876
            'compare_datetime_text',
6877
            '< allow_empty'
6878
        );
6879
6880
        $form->addElement('html', '</div>');
6881
6882
        $form->addCheckBox(
6883
            'send_subscription_notification',
6884
            [
6885
                get_lang('SendSubscriptionNotification'),
6886
                get_lang('SendAnEmailWhenAUserBeingSubscribed')
6887
            ]
6888
        );
6889
6890
        // Extra fields
6891
        $extra_field = new ExtraField('session');
6892
        $extra = $extra_field->addElements($form, $sessionId);
6893
6894
        $form->addElement('html','</div>');
6895
6896
        $js = $extra['jquery_ready_content'];
6897
6898
        return ['js' => $js];
6899
    }
6900
6901
    /**
6902
     * Gets the number of rows in the session table filtered through the given
6903
     * array of parameters
6904
     * @param array Array of options/filters/keys
6905
     * @return integer The number of rows, or false on wrong param
6906
     * @assert ('a') === false
6907
     */
6908
    static function get_count_admin_complete($options = array())
6909
    {
6910
        if (!is_array($options)) {
6911
            return false;
6912
        }
6913
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
6914
        $tbl_session_category = Database::get_main_table(TABLE_MAIN_SESSION_CATEGORY);
6915
        $tbl_user = Database::get_main_table(TABLE_MAIN_USER);
6916
        $sessionCourseUserTable = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
6917
        $courseTable = Database::get_main_table(TABLE_MAIN_COURSE);
6918
6919
        $where = 'WHERE 1 = 1 ';
6920
        $user_id = api_get_user_id();
6921
6922
        if (api_is_session_admin() &&
6923
            api_get_setting('allow_session_admins_to_see_all_sessions') == 'false'
6924
        ) {
6925
            $where.=" WHERE s.session_admin_id = $user_id ";
6926
        }
6927
6928 View Code Duplication
        if (!empty($options['where'])) {
6929
            $options['where'] = str_replace('course_title', 'c.title', $options['where']);
6930
            $options['where'] = str_replace("( session_active = '0' )", '1=1',  $options['where']);
6931
6932
            $options['where'] = str_replace(
6933
                array("AND session_active = '1'  )", " AND (  session_active = '1'  )"),
6934
                array(') GROUP BY s.name HAVING session_active = 1 ', " GROUP BY s.name HAVING session_active = 1 " )
6935
                , $options['where']
6936
            );
6937
6938
            $options['where'] = str_replace(
6939
                array("AND session_active = '0'  )", " AND (  session_active = '0'  )"),
6940
                array(') GROUP BY s.name HAVING session_active = 0 ', " GROUP BY s.name HAVING session_active = '0' "),
6941
                $options['where']
6942
            );
6943
6944
            if (!empty($options['extra'])) {
6945
                $options['where'] = str_replace(' 1 = 1  AND', '', $options['where']);
6946
                $options['where'] = str_replace('AND', 'OR', $options['where']);
6947
6948
                foreach ($options['extra'] as $extra) {
6949
                    $options['where'] = str_replace($extra['field'], 'fv.field_id = '.$extra['id'].' AND fvo.option_value', $options['where']);
6950
                }
6951
            }
6952
            $where .= ' AND '.$options['where'];
6953
        }
6954
6955
        $today = api_get_utc_datetime();
6956
        $query_rows = "SELECT count(*) as total_rows, c.title as course_title, s.name,
6957
                        IF (
6958
                            (s.access_start_date <= '$today' AND '$today' < s.access_end_date) OR
6959
                            (s.access_start_date = '0000-00-00 00:00:00' AND s.access_end_date = '0000-00-00 00:00:00' ) OR
6960
                            (s.access_start_date IS NULL AND s.access_end_date IS NULL) OR
6961
                            (s.access_start_date <= '$today' AND ('0000-00-00 00:00:00' = s.access_end_date OR s.access_end_date IS NULL )) OR
6962
                            ('$today' < s.access_end_date AND ('0000-00-00 00:00:00' = s.access_start_date OR s.access_start_date IS NULL) )
6963
                        , 1, 0) as session_active
6964
                       FROM $tbl_session s
6965
                       LEFT JOIN  $tbl_session_category sc
6966
                       ON s.session_category_id = sc.id
6967
                       INNER JOIN $tbl_user u
6968
                       ON s.id_coach = u.user_id
6969
                       INNER JOIN $sessionCourseUserTable scu
6970
                       ON s.id = scu.session_id
6971
                       INNER JOIN $courseTable c
6972
                       ON c.id = scu.c_id
6973
                       $where ";
6974
6975
        if (api_is_multiple_url_enabled()) {
6976
            $table_access_url_rel_session= Database::get_main_table(TABLE_MAIN_ACCESS_URL_REL_SESSION);
6977
            $access_url_id = api_get_current_access_url_id();
6978
            if ($access_url_id != -1) {
6979
                $where.= " AND ar.access_url_id = $access_url_id ";
6980
6981
                $query_rows = "SELECT count(*) as total_rows
6982
                               FROM $tbl_session s
6983
                               LEFT JOIN  $tbl_session_category sc
6984
                               ON s.session_category_id = sc.id
6985
                               INNER JOIN $tbl_user u
6986
                               ON s.id_coach = u.user_id
6987
                               INNER JOIN $table_access_url_rel_session ar
6988
                               ON ar.session_id = s.id $where ";
6989
            }
6990
        }
6991
6992
        $result = Database::query($query_rows);
6993
        $num = 0;
6994
        if (Database::num_rows($result)) {
6995
            $rows = Database::fetch_array($result);
6996
            $num = $rows['total_rows'];
6997
        }
6998
6999
        return $num;
7000
    }
7001
7002
    /**
7003
     * @param string $list_type
7004
     * @return array
7005
     */
7006
    public static function getGridColumns($list_type = 'simple')
7007
    {
7008
        // Column config
7009
        $operators = array('cn', 'nc');
7010
        $date_operators = array('gt', 'ge', 'lt', 'le');
7011
7012
        switch ($list_type) {
7013
            case 'simple':
7014
                $columns = array(
7015
                    get_lang('Name'),
7016
                    get_lang('Category'),
7017
                    get_lang('SessionDisplayStartDate'),
7018
                    get_lang('SessionDisplayEndDate'),
7019
                    //get_lang('Coach'),
7020
                    //get_lang('Status'),
7021
                    //get_lang('CourseTitle'),
7022
                    get_lang('Visibility'),
7023
                );
7024
                $column_model = array (
7025
                    array('name'=>'name', 'index'=>'s.name', 'width'=>'160',  'align'=>'left', 'search' => 'true', 'searchoptions' => array('sopt' => $operators)),
7026
                    array('name'=>'category_name', 'index'=>'category_name', 'width'=>'40',  'align'=>'left', 'search' => 'true', 'searchoptions' => array('sopt' => $operators)),
7027
                    array('name'=>'display_start_date', 'index'=>'display_start_date', 'width'=>'50',   'align'=>'left', 'search' => 'true', 'searchoptions' => array('dataInit' => 'date_pick_today', 'sopt' => $date_operators)),
7028
                    array('name'=>'display_end_date', 'index'=>'display_end_date', 'width'=>'50',   'align'=>'left', 'search' => 'true', 'searchoptions' => array('dataInit' => 'date_pick_one_month', 'sopt' => $date_operators)),
7029
                    array('name'=>'visibility', 'index'=>'visibility',      'width'=>'40',   'align'=>'left', 'search' => 'false'),
7030
                );
7031
                break;
7032
            case 'complete':
7033
                $columns = array(
7034
                    get_lang('Name'),
7035
                    get_lang('SessionDisplayStartDate'),
7036
                    get_lang('SessionDisplayEndDate'),
7037
                    get_lang('Coach'),
7038
                    get_lang('Status'),
7039
                    get_lang('Visibility'),
7040
                    get_lang('CourseTitle'),
7041
                );
7042
                $column_model = array (
7043
                    array('name'=>'name', 'index'=>'s.name', 'width'=>'200',  'align'=>'left', 'search' => 'true', 'searchoptions' => array('sopt' => $operators)),
7044
                    array('name'=>'display_start_date', 'index'=>'display_start_date', 'width'=>'70',   'align'=>'left', 'search' => 'true', 'searchoptions' => array('dataInit' => 'date_pick_today', 'sopt' => $date_operators)),
7045
                    array('name'=>'display_end_date', 'index'=>'display_end_date', 'width'=>'70',   'align'=>'left', 'search' => 'true', 'searchoptions' => array('dataInit' => 'date_pick_one_month', 'sopt' => $date_operators)),
7046
                    array('name'=>'coach_name', 'index'=>'coach_name',     'width'=>'70',   'align'=>'left', 'search' => 'false', 'searchoptions' => array('sopt' => $operators)),
7047
                    array('name'=>'session_active', 'index'=>'session_active', 'width'=>'25',   'align'=>'left', 'search' => 'true', 'stype'=>'select',
7048
                        // for the bottom bar
7049
                        'searchoptions' => array(
7050
                            'defaultValue'  => '1',
7051
                            'value'         => '1:'.get_lang('Active').';0:'.get_lang('Inactive')),
7052
                        // for the top bar
7053
                        'editoptions' => array('value' => '" ":'.get_lang('All').';1:'.get_lang('Active').';0:'.get_lang('Inactive')),
7054
                    ),
7055
                    array('name'=>'visibility',     'index'=>'visibility',      'width'=>'40',   'align'=>'left', 'search' => 'false'),
7056
                    array('name'=>'course_title',    'index'=>'course_title',   'width'=>'50',   'hidden' => 'true', 'search' => 'true', 'searchoptions' => array('searchhidden' =>'true','sopt' => $operators)),
7057
                );
7058
                break;
7059
        }
7060
7061
        // Inject extra session fields
7062
        $session_field = new ExtraField('session');
7063
        $rules = $session_field->getRules($columns, $column_model);
7064
7065
        $column_model[] = array('name'=>'actions', 'index'=>'actions', 'width'=>'80',  'align'=>'left','formatter'=>'action_formatter','sortable'=>'false', 'search' => 'false');
7066
        $columns[] = get_lang('Actions');
7067
7068
        foreach ($column_model as $col_model) {
7069
            $simple_column_name[] = $col_model['name'];
7070
        }
7071
7072
        $return_array =  array(
7073
            'columns' => $columns,
7074
            'column_model' => $column_model,
7075
            'rules' => $rules,
7076
            'simple_column_name' => $simple_column_name,
7077
        );
7078
7079
        return $return_array;
7080
    }
7081
7082
    /**
7083
     * Converts all dates sent through the param array (given form) to correct dates with timezones
7084
     * @param array The dates The same array, with times converted
7085
     * @param boolean $applyFormat Whether apply the DATE_TIME_FORMAT_SHORT format for sessions
7086
     * @return array The same array, with times converted
7087
     */
7088
    static function convert_dates_to_local($params, $applyFormat = false)
7089
    {
7090
        if (!is_array($params)) {
7091
            return false;
7092
        }
7093
        $params['display_start_date'] = api_get_local_time($params['display_start_date'], null, null, true);
7094
        $params['display_end_date'] = api_get_local_time($params['display_end_date'], null, null, true);
7095
7096
        $params['access_start_date'] = api_get_local_time($params['access_start_date'], null, null, true);
7097
        $params['access_end_date'] = api_get_local_time($params['access_end_date'], null, null, true);
7098
7099
        $params['coach_access_start_date'] = isset($params['coach_access_start_date']) ? api_get_local_time($params['coach_access_start_date'], null, null, true) : null;
7100
        $params['coach_access_end_date'] = isset($params['coach_access_end_date']) ? api_get_local_time($params['coach_access_end_date'], null, null, true) : null;
7101
7102
        if ($applyFormat) {
7103 View Code Duplication
            if (isset($params['display_start_date'])) {
7104
                $params['display_start_date'] = api_format_date($params['display_start_date'], DATE_TIME_FORMAT_SHORT);
7105
            }
7106
7107 View Code Duplication
            if (isset($params['display_end_date'])) {
7108
                $params['display_end_date'] = api_format_date($params['display_end_date'], DATE_TIME_FORMAT_SHORT);
7109
            }
7110
7111 View Code Duplication
            if (isset($params['access_start_date'])) {
7112
                $params[''] = api_format_date($params['access_start_date'], DATE_TIME_FORMAT_SHORT);
7113
            }
7114
7115 View Code Duplication
            if (isset($params['access_end_date'])) {
7116
                $params['access_end_date'] = api_format_date($params['access_end_date'], DATE_TIME_FORMAT_SHORT);
7117
            }
7118
7119 View Code Duplication
            if (isset($params['coach_access_start_date'])) {
7120
                $params['coach_access_start_date'] = api_format_date($params['coach_access_start_date'], DATE_TIME_FORMAT_SHORT);
7121
            }
7122
7123 View Code Duplication
            if (isset($params['coach_access_end_date'])) {
7124
                $params['coach_access_end_date'] = api_format_date($params['coach_access_end_date'], DATE_TIME_FORMAT_SHORT);
7125
            }
7126
        }
7127
7128
        return $params;
7129
    }
7130
7131
    /**
7132
     * Gets the admin session list callback of the session/session_list.php
7133
     * page with all user/details in the right fomat
7134
     * @param array
7135
     * @result array Array of rows results
7136
     * @asset ('a') === false
7137
     */
7138
    public static function get_sessions_admin_complete($options = array())
7139
    {
7140
        if (!is_array($options)) {
7141
            return false;
7142
        }
7143
7144
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
7145
        $tbl_session_category = Database::get_main_table(TABLE_MAIN_SESSION_CATEGORY);
7146
        $tbl_user = Database::get_main_table(TABLE_MAIN_USER);
7147
        $tbl_session_rel_course = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
7148
        $tbl_course = Database::get_main_table(TABLE_MAIN_COURSE);
7149
7150
        $extraFieldTable = Database::get_main_table(TABLE_EXTRA_FIELD);
7151
        $tbl_session_field_values = Database::get_main_table(TABLE_EXTRA_FIELD_VALUES);
7152
        $tbl_session_field_options = Database::get_main_table(TABLE_EXTRA_FIELD_OPTIONS);
7153
7154
        $where = 'WHERE 1 = 1 ';
7155
        $user_id = api_get_user_id();
7156
7157 View Code Duplication
        if (!api_is_platform_admin()) {
7158
            if (api_is_session_admin() &&
7159
                api_get_setting('allow_session_admins_to_manage_all_sessions') == 'false'
7160
            ) {
7161
                $where.=" AND s.session_admin_id = $user_id ";
7162
            }
7163
        }
7164
7165
        $coach_name = " CONCAT(u.lastname , ' ', u.firstname) as coach_name ";
7166
        if (api_is_western_name_order()) {
7167
            $coach_name = " CONCAT(u.firstname, ' ', u.lastname) as coach_name ";
7168
        }
7169
7170
        $today = api_get_utc_datetime();
7171
        $inject_extra_fields = null;
7172
        $extra_fields = array();
7173
        $extra_fields_info = array();
7174
7175
        //for now only sessions
7176
        $extra_field = new ExtraField('session');
7177
        $double_fields = array();
7178
7179
        $extra_field_option = new ExtraFieldOption('session');
7180
7181
        if (isset($options['extra'])) {
7182
            $extra_fields = $options['extra'];
7183
            if (!empty($extra_fields)) {
7184
                foreach ($extra_fields as $extra) {
7185
                    $inject_extra_fields .= " IF (fv.field_id = {$extra['id']}, fvo.option_display_text, NULL ) as {$extra['field']} , ";
7186 View Code Duplication
                    if (isset($extra_fields_info[$extra['id']])) {
7187
                        $info = $extra_fields_info[$extra['id']];
7188
                    } else {
7189
                        $info = $extra_field->get($extra['id']);
7190
                        $extra_fields_info[$extra['id']] = $info;
7191
                    }
7192
7193
                    if ($info['field_type'] == ExtraField::FIELD_TYPE_DOUBLE_SELECT) {
7194
                        $double_fields[$info['id']] = $info;
7195
                    }
7196
                }
7197
            }
7198
        }
7199
7200
        $options_by_double = array();
7201 View Code Duplication
        foreach ($double_fields as $double) {
7202
            $my_options = $extra_field_option->get_field_options_by_field(
7203
                $double['id'],
7204
                true
7205
            );
7206
            $options_by_double['extra_'.$double['field_variable']] = $my_options;
7207
        }
7208
7209
        //sc.name as category_name,
7210
        $select = "
7211
                SELECT * FROM (
7212
                    SELECT DISTINCT
7213
                         IF (
7214
                            (s.access_start_date <= '$today' AND '$today' < s.access_end_date) OR
7215
                            (s.access_start_date = '0000-00-00 00:00:00' AND s.access_end_date = '0000-00-00 00:00:00' ) OR
7216
                            (s.access_start_date IS NULL AND s.access_end_date IS NULL) OR
7217
                            (s.access_start_date <= '$today' AND ('0000-00-00 00:00:00' = s.access_end_date OR s.access_end_date IS NULL )) OR
7218
                            ('$today' < s.access_end_date AND ('0000-00-00 00:00:00' = s.access_start_date OR s.access_start_date IS NULL) )
7219
                        , 1, 0) as session_active,
7220
                s.name,
7221
                s.nbr_courses,
7222
                s.nbr_users,
7223
                s.display_start_date,
7224
                s.display_end_date,
7225
                $coach_name,
7226
                access_start_date,
7227
                access_end_date,
7228
                s.visibility,
7229
                u.user_id,
7230
                $inject_extra_fields
7231
                c.title as course_title,
7232
                s.id ";
7233
7234 View Code Duplication
        if (!empty($options['where'])) {
7235
            if (!empty($options['extra'])) {
7236
                $options['where'] = str_replace(' 1 = 1  AND', '', $options['where']);
7237
                $options['where'] = str_replace('AND', 'OR', $options['where']);
7238
                foreach ($options['extra'] as $extra) {
7239
                    $options['where'] = str_replace($extra['field'], 'fv.field_id = '.$extra['id'].' AND fvo.option_value', $options['where']);
7240
                }
7241
            }
7242
            $options['where'] = str_replace('course_title', 'c.title', $options['where']);
7243
7244
            $options['where'] = str_replace("( session_active = '0' )", '1=1',  $options['where']);
7245
7246
            $options['where'] = str_replace(
7247
                array("AND session_active = '1'  )", " AND (  session_active = '1'  )"),
7248
                array(') GROUP BY s.name HAVING session_active = 1 ', " GROUP BY s.name HAVING session_active = 1 " )
7249
                , $options['where']
7250
            );
7251
7252
            $options['where'] = str_replace(
7253
                array("AND session_active = '0'  )", " AND (  session_active = '0'  )"),
7254
                array(') GROUP BY s.name HAVING session_active = 0 ', " GROUP BY s.name HAVING session_active = '0' "),
7255
                $options['where']
7256
            );
7257
7258
7259
            $where .= ' AND '.$options['where'];
7260
        }
7261
7262
        if (!empty($options['limit'])) {
7263
            $where .= " LIMIT ".$options['limit'];
7264
        }
7265
        $query = "$select FROM $tbl_session s
7266
                    LEFT JOIN $tbl_session_field_values fv
7267
                    ON (fv.item_id = s.id)
7268
                    LEFT JOIN $extraFieldTable f
7269
                    ON f.id = fv.field_id
7270
                    LEFT JOIN $tbl_session_field_options fvo
7271
                    ON (fv.field_id = fvo.field_id)
7272
                    LEFT JOIN $tbl_session_rel_course src
7273
                    ON (src.session_id = s.id)
7274
                    LEFT JOIN $tbl_course c
7275
                    ON (src.c_id = c.id)
7276
                    LEFT JOIN $tbl_session_category sc
7277
                    ON (s.session_category_id = sc.id)
7278
                    INNER JOIN $tbl_user u
7279
                    ON (s.id_coach = u.user_id) ".
7280
            $where;
7281
7282 View Code Duplication
        if (api_is_multiple_url_enabled()) {
7283
            $table_access_url_rel_session= Database::get_main_table(TABLE_MAIN_ACCESS_URL_REL_SESSION);
7284
            $access_url_id = api_get_current_access_url_id();
7285
            if ($access_url_id != -1) {
7286
                $where.= " AND ar.access_url_id = $access_url_id ";
7287
                $query = "$select
7288
                    FROM $tbl_session s
7289
                    LEFT JOIN $tbl_session_field_values fv ON (fv.session_id = s.id)
7290
                    LEFT JOIN $tbl_session_field_options fvo ON (fv.field_id = fvo.field_id)
7291
                    LEFT JOIN $tbl_session_rel_course src ON (src.id_session = s.id)
7292
                    LEFT JOIN $tbl_course c ON (src.c_id = c.id)
7293
                    LEFT JOIN $tbl_session_category sc ON (s.session_category_id = sc.id)
7294
                    INNER JOIN $tbl_user u ON (s.id_coach = u.user_id)
7295
                    INNER JOIN $table_access_url_rel_session ar ON (ar.session_id = s.id)
7296
                    $where";
7297
            }
7298
        }
7299
7300
        $query .= ") AS session_table";
7301
7302
        if (!empty($options['order'])) {
7303
            $query .= " ORDER BY ".$options['order'];
7304
        }
7305
7306
        //error_log($query);
7307
        //echo $query;
7308
7309
        $result = Database::query($query);
7310
        $formatted_sessions = array();
7311
7312
        if (Database::num_rows($result)) {
7313
            $sessions   = Database::store_result($result, 'ASSOC');
7314
            foreach ($sessions as $session) {
7315
                $session_id = $session['id'];
7316
                $session['name'] = Display::url($session['name'], "resume_session.php?id_session=".$session['id']);
7317
                $session['coach_name'] = Display::url($session['coach_name'], "user_information.php?user_id=".$session['user_id']);
7318 View Code Duplication
                if ($session['session_active'] == 1) {
7319
                    $session['session_active'] = Display::return_icon('accept.png', get_lang('Active'), array(), ICON_SIZE_SMALL);
7320
                } else {
7321
                    $session['session_active'] = Display::return_icon('error.png', get_lang('Inactive'), array(), ICON_SIZE_SMALL);
7322
                }
7323
7324
                $session = self::convert_dates_to_local($session);
7325
7326 View Code Duplication
                switch ($session['visibility']) {
7327
                    case SESSION_VISIBLE_READ_ONLY: //1
7328
                        $session['visibility'] =  get_lang('ReadOnly');
7329
                        break;
7330
                    case SESSION_VISIBLE:           //2
7331
                    case SESSION_AVAILABLE:         //4
7332
                        $session['visibility'] =  get_lang('Visible');
7333
                        break;
7334
                    case SESSION_INVISIBLE:         //3
7335
                        $session['visibility'] =  api_ucfirst(get_lang('Invisible'));
7336
                        break;
7337
                }
7338
7339
                // Cleaning double selects
7340 View Code Duplication
                foreach ($session as $key => &$value) {
0 ignored issues
show
Bug introduced by
The expression $session of type false|array<string,strin...d_date":"string|null"}> is not guaranteed to be traversable. How about adding an additional type check?

There are different options of fixing this problem.

  1. If you want to be on the safe side, you can add an additional type-check:

    $collection = json_decode($data, true);
    if ( ! is_array($collection)) {
        throw new \RuntimeException('$collection must be an array.');
    }
    
    foreach ($collection as $item) { /** ... */ }
    
  2. If you are sure that the expression is traversable, you might want to add a doc comment cast to improve IDE auto-completion and static analysis:

    /** @var array $collection */
    $collection = json_decode($data, true);
    
    foreach ($collection as $item) { /** .. */ }
    
  3. Mark the issue as a false-positive: Just hover the remove button, in the top-right corner of this issue for more options.

Loading history...
7341
                    if (isset($options_by_double[$key]) || isset($options_by_double[$key.'_second'])) {
7342
                        $options = explode('::', $value);
7343
                    }
7344
                    $original_key = $key;
7345
7346
                    if (strpos($key, '_second') === false) {
0 ignored issues
show
Unused Code introduced by
This if statement is empty and can be removed.

This check looks for the bodies of if statements that have no statements or where all statements have been commented out. This may be the result of changes for debugging or the code may simply be obsolete.

These if bodies can be removed. If you have an empty if but statements in the else branch, consider inverting the condition.

if (rand(1, 6) > 3) {
//print "Check failed";
} else {
    print "Check succeeded";
}

could be turned into

if (rand(1, 6) <= 3) {
    print "Check succeeded";
}

This is much more concise to read.

Loading history...
7347
                    } else {
7348
                        $key = str_replace('_second', '', $key);
7349
                    }
7350
7351
                    if (isset($options_by_double[$key])) {
7352
                        if (isset($options[0])) {
7353
                            if (isset($options_by_double[$key][$options[0]])) {
7354
                                if (strpos($original_key, '_second') === false) {
7355
                                    $value = $options_by_double[$key][$options[0]]['option_display_text'];
7356
                                } else {
7357
                                    $value = $options_by_double[$key][$options[1]]['option_display_text'];
7358
                                }
7359
                            }
7360
                        }
7361
                    }
7362
                }
7363
7364
                // Magic filter
7365
                if (isset($formatted_sessions[$session_id])) {
7366
                    $formatted_sessions[$session_id] = self::compareArraysToMerge($formatted_sessions[$session_id], $session);
0 ignored issues
show
Security Bug introduced by
It seems like $session defined by self::convert_dates_to_local($session) on line 7324 can also be of type false; however, SessionManager::compareArraysToMerge() does only seem to accept array, did you maybe forget to handle an error condition?

This check looks for type mismatches where the missing type is false. This is usually indicative of an error condtion.

Consider the follow example

<?php

function getDate($date)
{
    if ($date !== null) {
        return new DateTime($date);
    }

    return false;
}

This function either returns a new DateTime object or false, if there was an error. This is a typical pattern in PHP programming to show that an error has occurred without raising an exception. The calling code should check for this returned false before passing on the value to another function or method that may not be able to handle a false.

Loading history...
7367
                } else {
7368
                    $formatted_sessions[$session_id] = $session;
7369
                }
7370
            }
7371
        }
7372
7373
        return $formatted_sessions;
7374
    }
7375
7376
    /**
7377
     * Compare two arrays
7378
     * @param array $array1
7379
     * @param array $array2
7380
     *
7381
     * @return array
7382
     */
7383
    static function compareArraysToMerge($array1, $array2)
7384
    {
7385
        if (empty($array2)) {
7386
            return $array1;
7387
        }
7388
        foreach ($array1 as $key => $item) {
7389
            if (!isset($array1[$key])) {
7390
                //My string is empty try the other one
7391
                if (isset($array2[$key]) && !empty($array2[$key])) {
7392
                    $array1[$key] = $array2[$key];
7393
                }
7394
            }
7395
        }
7396
        return $array1;
7397
    }
7398
7399
    /**
7400
     * Get link to the admin page for this session
7401
     * @param   int $id Session ID
7402
     * @return mixed    URL to the admin page to manage the session, or false on error
7403
     */
7404
    public static function getAdminPath($id)
7405
    {
7406
        $id = intval($id);
7407
        $session = self::fetch($id);
7408
        if (empty($session)) {
7409
            return false;
7410
        }
7411
        return api_get_path(WEB_CODE_PATH) . 'session/resume_session.php?id_session=' . $id;
7412
    }
7413
7414
    /**
7415
     * Get link to the user page for this session.
7416
     * If a course is provided, build the link to the course
7417
     * @param   int $id Session ID
7418
     * @param   int $courseId Course ID (optional) in case the link has to send straight to the course
7419
     * @return mixed    URL to the page to use the session, or false on error
7420
     */
7421
    public static function getPath($id, $courseId = 0)
7422
    {
7423
        $id = intval($id);
7424
        $session = self::fetch($id);
7425
        if (empty($session)) {
7426
            return false;
7427
        }
7428
        if (empty($courseId)) {
7429
            return api_get_path(WEB_CODE_PATH) . 'session/index.php?session_id=' . $id;
7430
        } else {
7431
            $courseInfo = api_get_course_info_by_id($courseId);
7432
            if ($courseInfo) {
7433
                return $courseInfo['course_public_url'].'?id_session='.$id;
7434
            }
7435
        }
7436
7437
        return false;
7438
    }
7439
7440
    /**
7441
     * Return an associative array 'id_course' => [id_session1, id_session2...]
7442
     * where course id_course is in sessions id_session1, id_session2
7443
     * for course where user is coach
7444
     * i.e. coach for the course or
7445
     * main coach for a session the course is in
7446
     * for a session category (or woth no session category if empty)
7447
     *
7448
     * @param $userId
7449
     *
7450
     * @return array
7451
     */
7452
    public static function getSessionCourseForUser($userId)
7453
    {
7454
        // list of COURSES where user is COURSE session coach
7455
        $listCourseCourseCoachSession = self::getCoursesForCourseSessionCoach($userId);
7456
7457
        // list of courses where user is MAIN session coach
7458
        $listCourseMainCoachSession = self::getCoursesForMainSessionCoach($userId);
7459
7460
        // merge these 2 array
7461
        $listResCourseSession = $listCourseCourseCoachSession;
7462
        foreach ($listCourseMainCoachSession as $courseId2 => $listSessionId2) {
7463
            if (isset($listResCourseSession[$courseId2])) {
7464
                // if sessionId array exists for this course
7465
                // same courseId, merge the list of session
7466
                foreach ($listCourseMainCoachSession[$courseId2] as $i => $sessionId2) {
7467
                    if (!in_array($sessionId2, $listResCourseSession[$courseId2])) {
7468
                        $listResCourseSession[$courseId2][] = $sessionId2;
7469
                    }
7470
                }
7471
            } else {
7472
                $listResCourseSession[$courseId2] = $listSessionId2;
7473
            }
7474
        }
7475
7476
        return $listResCourseSession;
7477
    }
7478
7479
    /**
7480
     * Return an associative array 'id_course' => [id_session1, id_session2...]
7481
     * where course id_course is in sessions id_session1, id_session2
7482
     * @param $userId
7483
     *
7484
     * @return array
7485
     */
7486
    public static function getCoursesForCourseSessionCoach($userId)
7487
    {
7488
        $listResCourseSession = array();
7489
        $tblCourse = Database::get_main_table(TABLE_MAIN_COURSE);
7490
        $tblSessionRelCourseRelUser = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
7491
7492
        $sql = "SELECT session_id, c_id, c.id
7493
                FROM $tblSessionRelCourseRelUser srcru
7494
                LEFT JOIN $tblCourse c
7495
                ON c.id = srcru.c_id
7496
                WHERE
7497
                    srcru.user_id =".intval($userId)." AND
7498
                    srcru.status = 2";
7499
7500
        $res = Database::query($sql);
7501
7502
        while ($data = Database::fetch_assoc($res)) {
7503
            if (self::isSessionDateOkForCoach($data['session_id'])) {
7504
                if (!isset($listResCourseSession[$data['id']])) {
7505
                    $listResCourseSession[$data['id']] = array();
7506
                }
7507
                $listResCourseSession[$data['id']][] = $data['session_id'];
7508
            }
7509
        }
7510
7511
        return $listResCourseSession;
7512
    }
7513
7514
    /**
7515
     * Return true if coach is allowed to access this session
7516
     * @param int $sessionId
7517
     * @return bool
7518
     */
7519
    public static function isSessionDateOkForCoach($sessionId)
7520
    {
7521
        return api_get_session_visibility($sessionId);
7522
        /*
7523
        $listSessionInfo = api_get_session_info($sessionId);
7524
        $dateStart = $listSessionInfo['date_start'];
7525
        $dateEnd = $listSessionInfo['date_end'];
7526
        $nbDaysAccessBeforeBeginning = $listSessionInfo['nb_days_access_before_beginning'];
7527
        $nbDaysAccessAfterEnd = $listSessionInfo['nb_days_access_after_end'];
7528
7529
        // no start date
7530
        if ($dateStart == '0000-00-00') {
7531
            return true;
7532
        }
7533
7534
        $now = time();
7535
7536
        $dateStartForCoach = api_strtotime($dateStart.' 00:00:00') - ($nbDaysAccessBeforeBeginning * 86400);
7537
        $dateEndForCoach = api_strtotime($dateEnd.' 00:00:00') + ($nbDaysAccessAfterEnd * 86400);
7538
7539
        if ($dateEnd == '0000-00-00') {
7540
            // start date but no end date
7541
            if ($dateStartForCoach <= $now) {
7542
                return true;
7543
            }
7544
        } else {
7545
            // start date and end date
7546
            if ($dateStartForCoach <= $now && $now <= $dateEndForCoach) {
7547
                return true;
7548
            }
7549
        }
7550
7551
        return false;*/
7552
    }
7553
7554
    /**
7555
     * Return an associative array 'id_course' => [id_session1, id_session2...]
7556
     * where course id_course is in sessions id_session1, id_session2
7557
     * @param $userId
7558
     *
7559
     * @return array
7560
     */
7561
    public static function getCoursesForMainSessionCoach($userId)
7562
    {
7563
        $listResCourseSession = array();
7564
        $tblSession = Database::get_main_table(TABLE_MAIN_SESSION);
7565
7566
        // list of SESSION where user is session coach
7567
        $sql = "SELECT id FROM $tblSession
7568
                WHERE id_coach = ".intval($userId);
7569
        $res = Database::query($sql);
7570
7571
        while ($data = Database::fetch_assoc($res)) {
7572
            $sessionId = $data['id'];
7573
            $listCoursesInSession = self::getCoursesInSession($sessionId);
7574
            foreach ($listCoursesInSession as $i => $courseId) {
7575
                if (self::isSessionDateOkForCoach($sessionId)) {
7576
                    if (!isset($listResCourseSession[$courseId])) {
7577
                        $listResCourseSession[$courseId] = array();
7578
                    }
7579
                    $listResCourseSession[$courseId][] = $sessionId;
7580
                }
7581
            }
7582
        }
7583
7584
        return $listResCourseSession;
7585
    }
7586
7587
    /**
7588
     * Return an array of course_id used in session $sessionId
7589
     * @param $sessionId
7590
     *
7591
     * @return array
7592
     */
7593
    public static function getCoursesInSession($sessionId)
7594
    {
7595
        $listResultsCourseId = array();
7596
        $tblSessionRelCourse = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
7597
        $tblCourse = Database::get_main_table(TABLE_MAIN_COURSE);
7598
7599
        // list of course in this session
7600
        $sql = "SELECT session_id, c.id
7601
                FROM $tblSessionRelCourse src
7602
                LEFT JOIN $tblCourse c
7603
                ON c.id = src.c_id
7604
                WHERE session_id = ".intval($sessionId);
7605
        $res = Database::query($sql);
7606
        while ($data = Database::fetch_assoc($res)) {
7607
            $listResultsCourseId[] = $data['id'];
7608
        }
7609
7610
        return $listResultsCourseId;
7611
    }
7612
7613
    /**
7614
     * Return an array of courses in session for user
7615
     * and for each courses the list of session that use this course for user
7616
     *
7617
     * [0] => array
7618
     *      userCatId
7619
     *      userCatTitle
7620
     *      courseInUserCatList
7621
     *          [0] => array
7622
     *              courseId
7623
     *              title
7624
     *              courseCode
7625
     *              sessionCatList
7626
     *                  [0] => array
7627
     *                      catSessionId
7628
     *                      catSessionName
7629
     *                      sessionList
7630
     *                          [0] => array
7631
     *                              sessionId
7632
     *                              sessionName
7633
     *
7634
     * @param $userId
7635
     *
7636
     * @return array
7637
     *
7638
     */
7639
    public static function getNamedSessionCourseForCoach($userId)
7640
    {
7641
        $listResults = array();
7642
        $listCourseSession = self::getSessionCourseForUser($userId);
7643
        foreach ($listCourseSession as $courseId => $listSessionId) {
7644
            // Course info
7645
            $courseInfo = api_get_course_info_by_id($courseId);
7646
            $listOneCourse = array();
7647
            $listOneCourse['courseId'] = $courseId;
7648
            $listOneCourse['title'] = $courseInfo['title'];
7649
            //$listOneCourse['courseCode'] = $courseInfo['code'];
7650
            $listOneCourse['course'] = $courseInfo;
7651
            $listOneCourse['sessionCatList'] = array();
7652
            $listCat = array();
7653
            foreach ($listSessionId as $i => $sessionId) {
7654
                // here we got all session for this course
7655
                // lets check there session categories
7656
                $sessionInfo = SessionManager::fetch($sessionId);
7657
                $catId = $sessionInfo['session_category_id'];
7658
                if (!isset($listCat[$catId])) {
7659
                    $listCatInfo = self::get_session_category($catId);
7660
                    $listCat[$catId] = array();
7661
                    $listCat[$catId]['catSessionId'] = $catId;
7662
                    $listCat[$catId]['catSessionName'] = $listCatInfo['name'];
7663
                    $listCat[$catId]['sessionList'] = array();
7664
                }
7665
                $listSessionInfo = SessionManager::fetch($sessionId);
7666
                $listSessionIdName = array(
7667
                    "sessionId" => $sessionId,
7668
                    "sessionName" => $listSessionInfo['name'],
7669
                );
7670
                $listCat[$catId]['sessionList'][] = $listSessionIdName;
7671
            }
7672
            // sort $listCat by catSessionName
7673
            usort($listCat, 'self::compareBySessionName');
7674
            // in each catSession sort sessionList by sessionName
7675
            foreach($listCat as $i => $listCatSessionInfo) {
7676
                $listSessionList = $listCatSessionInfo['sessionList'];
7677
                usort($listSessionList, 'self::compareCatSessionInfo');
7678
                $listCat[$i]['sessionList'] = $listSessionList;
7679
            }
7680
7681
            $listOneCourse['sessionCatList'] = $listCat;
7682
7683
            // user course category
7684
            list($userCatId, $userCatTitle) = CourseManager::getUserCourseCategoryForCourse(
7685
                $userId,
7686
                $courseId
7687
            );
7688
7689
            $userCatId = intval($userCatId);
7690
            $listResults[$userCatId]['courseInUserCategoryId'] =  $userCatId;
7691
            $listResults[$userCatId]['courseInUserCategoryTitle'] =  $userCatTitle;
7692
            $listResults[$userCatId]['courseInUserCatList'][] = $listOneCourse;
7693
        }
7694
7695
        // sort by user course cat
7696
        uasort($listResults, 'self::compareByUserCourseCat');
7697
7698
        // sort by course title
7699
        foreach ($listResults as $userCourseCatId => $tabCoursesInCat) {
7700
            $courseInUserCatList = $tabCoursesInCat['courseInUserCatList'];
7701
            uasort($courseInUserCatList, 'self::compareByCourse');
7702
            $listResults[$userCourseCatId]['courseInUserCatList'] = $courseInUserCatList;
7703
        }
7704
7705
        return $listResults;
7706
    }
7707
7708
    /**
7709
     * @param array $listA
7710
     * @param array $listB
7711
     * @return int
7712
     */
7713 View Code Duplication
    private static function compareCatSessionInfo($listA, $listB)
7714
    {
7715
        if ($listA['sessionName'] == $listB['sessionName']) {
7716
            return 0;
7717
        } else if($listA['sessionName'] > $listB['sessionName']) {
7718
            return 1;
7719
        } else {
7720
            return -1;
7721
        }
7722
    }
7723
7724
    /**
7725
     * @param array $listA
7726
     * @param array $listB
7727
     * @return int
7728
     */
7729
    private static function compareBySessionName($listA, $listB)
7730
    {
7731
        if ($listB['catSessionName'] == '') {
7732
            return -1;
7733
        } else if ($listA['catSessionName'] == '') {
7734
            return 1;
7735
        } else if ($listA['catSessionName'] == $listB['catSessionName']) {
7736
            return 0;
7737
        } else if($listA['catSessionName'] > $listB['catSessionName']) {
7738
            return 1;
7739
        } else {
7740
            return -1;
7741
        }
7742
    }
7743
7744
    /**
7745
     * @param array $listA
7746
     * @param array $listB
7747
     * @return int
7748
     */
7749 View Code Duplication
    private static function compareByUserCourseCat($listA, $listB)
7750
    {
7751
        if ($listA['courseInUserCategoryTitle'] == $listB['courseInUserCategoryTitle']) {
7752
            return 0;
7753
        } else if($listA['courseInUserCategoryTitle'] > $listB['courseInUserCategoryTitle']) {
7754
            return 1;
7755
        } else {
7756
            return -1;
7757
        }
7758
    }
7759
7760
    /**
7761
     * @param array $listA
7762
     * @param array $listB
7763
     * @return int
7764
     */
7765 View Code Duplication
    private static function compareByCourse($listA, $listB)
7766
    {
7767
        if ($listA['title'] == $listB['title']) {
7768
            return 0;
7769
        } else if($listA['title'] > $listB['title']) {
7770
            return 1;
7771
        } else {
7772
            return -1;
7773
        }
7774
    }
7775
7776
    /**
7777
     * Return HTML code for displaying session_course_for_coach
7778
     * @param $userId
7779
     * @return string
7780
     */
7781
    public static function getHtmlNamedSessionCourseForCoach($userId)
7782
    {
7783
        $htmlRes = '';
7784
7785
        $listInfo = self::getNamedSessionCourseForCoach($userId);
7786
        foreach ($listInfo as $i => $listCoursesInfo) {
7787
            $courseInfo = $listCoursesInfo['course'];
7788
            $courseCode = $listCoursesInfo['course']['code'];
7789
7790
            $listParamsCourse = array();
7791
            $listParamsCourse['icon'] = '<div style="float:left">
7792
                <input style="border:none;" type="button" onclick="$(\'#course-'.$courseCode.'\').toggle(\'fast\')" value="+" /></div>'.
7793
                Display::return_icon('blackboard.png', $courseInfo['title'], array(), ICON_SIZE_LARGE);
7794
            $listParamsCourse['link'] = '';
7795
            $listParamsCourse['title'] = Display::tag(
7796
                'a',
7797
                $courseInfo['title'],
7798
                array('href' => $listParamsCourse['link'])
7799
            );
7800
            $htmlCourse = '<div class="well" style="border-color:#27587D">'.
7801
                CourseManager::course_item_html($listParamsCourse, true);
7802
            // for each category of session
7803
            $htmlCatSessions = '';
7804
            foreach ($listCoursesInfo['sessionCatList'] as $j => $listCatSessionsInfo) {
7805
                // we got an array of session categories
7806
                $catSessionId = $listCoursesInfo['sessionCatList'][$j]['catSessionId'];
7807
                $catSessionName = $listCoursesInfo['sessionCatList'][$j]['catSessionName'];
7808
7809
                $listParamsCatSession['icon'] = Display::return_icon('folder_blue.png', $catSessionName, array(), ICON_SIZE_LARGE);
7810
                $listParamsCatSession['link'] = '';
7811
                $listParamsCatSession['title'] = $catSessionName;
7812
7813
                $marginShift = 20;
7814
                if ($catSessionName != '') {
7815
                    $htmlCatSessions .= '<div style="margin-left:'.$marginShift.'px;">' .
7816
                        CourseManager::course_item_html($listParamsCatSession, true) . '</div>';
7817
                    $marginShift = 40;
7818
                }
7819
7820
                // for each sessions
7821
                $listCatSessionSessionList = $listCoursesInfo['sessionCatList'][$j]['sessionList'];
7822
                $htmlSession = '';
7823
                foreach ($listCatSessionSessionList as $k => $listSessionInfo) {
7824
                    // we got an array of session info
7825
                    $sessionId = $listSessionInfo['sessionId'];
7826
                    $sessionName = $listSessionInfo['sessionName'];
7827
7828
                    $listParamsSession['icon'] = Display::return_icon('blackboard_blue.png', $sessionName, array(), ICON_SIZE_LARGE);
7829
                    $listParamsSession['link'] = '';
7830
                    $linkToCourseSession = $courseInfo['course_public_url'].'?id_session='.$sessionId;
7831
                    $listParamsSession['title'] =
7832
                        $sessionName.'<div style="font-weight:normal; font-style:italic">
7833
                            <a href="'.$linkToCourseSession.'">'.get_lang('GoToCourseInsideSession').'</a>
7834
                            </div>';
7835
                    $htmlSession .= '<div style="margin-left:'.$marginShift.'px;">'.
7836
                        CourseManager::course_item_html($listParamsSession, true).'</div>';
7837
                }
7838
                $htmlCatSessions .= $htmlSession;
7839
            }
7840
            $htmlRes .= $htmlCourse.'<div style="display:none" id="course-'.$courseCode.'">'.$htmlCatSessions.'</div></div>';
7841
        }
7842
7843
7844
7845
        return $htmlRes;
7846
    }
7847
}
7848