Completed
Push — 1.10.x ( 145b7c...a0ee00 )
by Yannick
128:28 queued 86:48
created

MySpace::get_connections_to_course_by_date()   B

Complexity

Conditions 3
Paths 2

Size

Total Lines 34
Code Lines 24

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 1 Features 0
Metric Value
cc 3
eloc 24
c 1
b 1
f 0
nc 2
nop 4
dl 0
loc 34
rs 8.8571
1
<?php
2
/* For licensing terms, see /license.txt */
3
4
use CpChart\Classes\pCache as pCache;
5
use CpChart\Classes\pData as pData;
6
use CpChart\Classes\pImage as pImage;
7
8
/**
9
 * Class MySpace
10
 * @package chamilo.reporting
11
 */
12
class MySpace
13
{
14
    /**
15
     * Get admin actions
16
     * @return string
17
     */
18
    public static function getAdminActions()
19
    {
20
        $actions = array(
21
            //array('url' => api_get_path(WEB_CODE_PATH).'mySpace/index.php', 'content' => get_lang('Home')),
22
            array('url' => api_get_path(WEB_CODE_PATH).'mySpace/admin_view.php?display=coaches', 'content' => get_lang('DisplayCoaches')),
23
            array('url' => api_get_path(WEB_CODE_PATH).'mySpace/admin_view.php?display=user', 'content' => get_lang('DisplayUserOverview')),
24
            array('url' => api_get_path(WEB_CODE_PATH).'mySpace/admin_view.php?display=session', 'content' => get_lang('DisplaySessionOverview')),
25
            array('url' => api_get_path(WEB_CODE_PATH).'mySpace/admin_view.php?display=course', 'content' => get_lang('DisplayCourseOverview')),
26
            array('url' => api_get_path(WEB_CODE_PATH).'tracking/question_course_report.php?view=admin', 'content' => get_lang('LPQuestionListResults')),
27
            array('url' => api_get_path(WEB_CODE_PATH).'tracking/course_session_report.php?view=admin', 'content' => get_lang('LPExerciseResultsBySession')),
28
            ['url' => api_get_path(WEB_CODE_PATH) . 'mySpace/admin_view.php?display=accessoverview', 'content' => get_lang('DisplayAccessOverview') . ' (' . get_lang('Beta') . ')']
29
        );
30
31
        return Display :: actions($actions, null);
32
    }
33
34
    public static function getTopMenu()
35
    {
36
        $menu_items = array();
37
        $menu_items[] = Display::url(Display::return_icon('stats.png', get_lang('MyStats'),'',ICON_SIZE_MEDIUM),api_get_path(WEB_CODE_PATH)."auth/my_progress.php" );
38
        $menu_items[] = Display::url(Display::return_icon('teacher.png', get_lang('TeacherInterface'), array(), 32), api_get_path(WEB_CODE_PATH).'mySpace/?view=teacher');
39
        $menu_items[] = Display::url(Display::return_icon('star_na.png', get_lang('AdminInterface'), array(), 32), '#');
40
        $menu_items[] = Display::url(Display::return_icon('quiz.png', get_lang('ExamTracking'), array(), 32), api_get_path(WEB_CODE_PATH).'tracking/exams.php');
41
        $menu = null;
42
        foreach ($menu_items as $item) {
43
            $menu .= $item;
44
        }
45
        $menu .= '<br />';
46
47
        return $menu;
48
    }
49
50
    /**
51
     * This function serves exporting data in CSV format.
52
     * @param array $header         The header labels.
53
     * @param array $data           The data array.
54
     * @param string $file_name     The name of the file which contains exported data.
55
     * @return string mixed             Returns a message (string) if an error occurred.
56
     */
57
    function export_csv($header, $data, $file_name = 'export.csv')
58
    {
59
        $archive_path = api_get_path(SYS_ARCHIVE_PATH);
60
        $archive_url = api_get_path(WEB_CODE_PATH).'course_info/download.php?archive=';
61
62
        if (!$open = fopen($archive_path.$file_name, 'w+')) {
63
            $message = get_lang('noOpen');
64
        } else {
65
            $info = '';
66
67
            foreach ($header as $value) {
68
                $info .= $value.';';
69
            }
70
            $info .= "\r\n";
71
72
            foreach ($data as $row) {
73
                foreach ($row as $value) {
74
                    $info .= $value.';';
75
                }
76
                $info .= "\r\n";
77
            }
78
79
            fwrite($open, $info);
80
            fclose($open);
81
            @chmod($file_name, api_get_permissions_for_new_files());
82
83
            header("Location:".$archive_url.$file_name);
84
        }
85
        return $message;
86
    }
87
88
    /**
89
     * Gets the connections to a course as an array of login and logout time
90
     *
91
     * @param   int     User ud
92
     * @param   int   $courseId
93
     * @param   int     Session id (optional, default = 0)
94
     * @return  array   Conections
95
     */
96
    static function get_connections_to_course($user_id, $courseId, $session_id = 0)
97
    {
98
        // Database table definitions
99
        $tbl_track_course = Database :: get_main_table(TABLE_STATISTIC_TRACK_E_COURSE_ACCESS);
100
101
        // protect data
102
        $user_id     = intval($user_id);
103
        $courseId = intval($courseId);
104
        $session_id  = intval($session_id);
105
106
        $sql = 'SELECT login_course_date, logout_course_date
107
                FROM ' . $tbl_track_course . '
108
                WHERE
109
                    user_id = '.$user_id.' AND
110
                    c_id = '.$courseId.' AND
111
                    session_id = '.$session_id.'
112
                ORDER BY login_course_date ASC';
113
        $rs = Database::query($sql);
114
        $connections = array();
115
116 View Code Duplication
        while ($row = Database::fetch_array($rs)) {
117
            $timestamp_login_date = api_strtotime($row['login_course_date'], 'UTC');
118
            $timestamp_logout_date = api_strtotime($row['logout_course_date'], 'UTC');
119
            $connections[] = array('login' => $timestamp_login_date, 'logout' => $timestamp_logout_date);
120
        }
121
122
        return $connections;
123
    }
124
125
    /**
126
     * @param $user_id
127
     * @param $course_list
128
     * @param int $session_id
129
     * @return array|bool
130
     */
131
    static function get_connections_from_course_list($user_id, $course_list, $session_id = 0)
132
    {
133
        // Database table definitions
134
        $tbl_track_course = Database :: get_main_table(TABLE_STATISTIC_TRACK_E_COURSE_ACCESS);
135
        if (empty($course_list)) {
136
            return false;
137
        }
138
139
        // protect data
140
        $user_id = intval($user_id);
141
        $session_id = intval($session_id);
142
        $new_course_list = array();
143
        foreach ($course_list as $course_item) {
144
            $courseInfo = api_get_course_info($course_item['code']);
145
            $courseId = $courseInfo['real_id'];
146
            $new_course_list[] =  '"'.$courseId.'"';
147
        }
148
        $course_list = implode(', ', $new_course_list);
149
150
        if (empty($course_list)) {
151
            return false;
152
        }
153
        $sql = 'SELECT login_course_date, logout_course_date, c_id
154
                FROM ' . $tbl_track_course . '
155
                WHERE
156
                    user_id = '.$user_id.' AND
157
                    c_id IN ('.$course_list.') AND
158
                    session_id = '.$session_id.'
159
                ORDER BY login_course_date ASC';
160
        $rs = Database::query($sql);
161
        $connections = array();
162
163 View Code Duplication
        while ($row = Database::fetch_array($rs)) {
164
            $timestamp_login_date = api_strtotime($row['login_course_date'], 'UTC');
165
            $timestamp_logout_date = api_strtotime($row['logout_course_date'], 'UTC');
166
            $connections[] = array(
167
                'login' => $timestamp_login_date,
168
                'logout' => $timestamp_logout_date,
169
                'c_id' => $row['c_id']
170
            );
171
        }
172
173
        return $connections;
174
    }
175
176
    /**
177
     * Creates a small table in the last column of the table with the user overview
178
     *
179
     * @param integer $user_id the id of the user
180
     * @param array $url_params additonal url parameters
181
     * @param array $row the row information (the other columns)
182
     * @return string html code
183
     */
184
    public static function course_info_tracking_filter($user_id, $url_params, $row)
185
    {
186
        // the table header
187
        $return = '<table class="data_table" style="width: 100%;border:0;padding:0;border-collapse:collapse;table-layout: fixed">';
188
        /*$return .= '  <tr>';
189
        $return .= '        <th>'.get_lang('Course').'</th>';
190
        $return .= '        <th>'.get_lang('AvgTimeSpentInTheCourse').'</th>';
191
        $return .= '        <th>'.get_lang('AvgStudentsProgress').'</th>';
192
        $return .= '        <th>'.get_lang('AvgCourseScore').'</th>';
193
        $return .= '        <th>'.get_lang('AvgExercisesScore').'</th>';
194
        $return .= '        <th>'.get_lang('AvgMessages').'</th>';
195
        $return .= '        <th>'.get_lang('AvgAssignments').'</th>';
196
        $return .= '        <th>'.get_lang('TotalExercisesScoreObtained').'</th>';
197
        $return .= '        <th>'.get_lang('TotalExercisesScorePossible').'</th>';
198
        $return .= '        <th>'.get_lang('TotalExercisesAnswered').'</th>';
199
        $return .= '        <th>'.get_lang('TotalExercisesScorePercentage').'</th>';
200
        $return .= '        <th>'.get_lang('FirstLogin').'</th>';
201
        $return .= '        <th>'.get_lang('LatestLogin').'</th>';
202
        $return .= '    </tr>';*/
203
204
        // database table definition
205
        $tbl_course_user = Database :: get_main_table(TABLE_MAIN_COURSE_USER);
206
207
        // getting all the courses of the user
208
        $sql = "SELECT * FROM $tbl_course_user
209
                WHERE
210
                    user_id = '".intval($user_id)."' AND
211
                    relation_type<>".COURSE_RELATION_TYPE_RRHH." ";
212
        $result = Database::query($sql);
213
        while ($row = Database::fetch_array($result)) {
214
            $courseInfo = api_get_course_info_by_id($row['c_id']);
215
            if (empty($courseInfo)) {
216
                continue;
217
            }
218
219
            $courseCode = $courseInfo['code'];
220
            $courseId = $courseInfo['real_id'];
221
222
            $return .= '<tr>';
223
            // course code
224
            $return .= '    <td width="157px" >'.cut($courseCode, 20, true).'</td>';
225
            // time spent in the course
226
            $return .= '    <td><div>'.api_time_to_hms(Tracking :: get_time_spent_on_the_course($user_id, $courseId)).'</div></td>';
227
            // student progress in course
228
            $return .= '    <td><div>'.round(Tracking :: get_avg_student_progress($user_id, $courseCode), 2).'</div></td>';
229
            // student score
230
            $avg_score = Tracking :: get_avg_student_score($user_id, $courseCode);
231
            if (is_numeric($avg_score)) {
232
                $avg_score = round($avg_score,2);
233
            } else {
234
                $$avg_score = '-';
235
            }
236
237
            $return .= '    <td><div>'.$avg_score.'</div></td>';
238
            // student tes score
239
            //$return .= '  <td><div style="width:40px">'.round(Tracking :: get_avg_student_exercise_score ($user_id, $courseCode),2).'%</div></td>';
240
            // student messages
241
            $return .= '    <td><div>'.Tracking :: count_student_messages($user_id, $courseCode).'</div></td>';
242
            // student assignments
243
            $return .= '    <td><div>'.Tracking :: count_student_assignments($user_id, $courseCode).'</div></td>';
244
            // student exercises results (obtained score, maximum score, number of exercises answered, score percentage)
245
            $exercises_results = MySpace::exercises_results($user_id, $courseCode);
246
            $return .= '    <td width="105px"><div>'.(is_null($exercises_results['percentage']) ? '' : $exercises_results['score_obtained'].'/'.$exercises_results['score_possible'].' ( '.$exercises_results['percentage'].'% )').'</div></td>';
247
            //$return .= '  <td><div>'.$exercises_results['score_possible'].'</div></td>';
248
            $return .= '    <td><div>'.$exercises_results['questions_answered'].'</div></td>';
249
            $return .= '    <td><div>'.Tracking :: get_last_connection_date_on_the_course($user_id, $courseInfo).'</div></td>';
250
            $return .= '<tr>';
251
        }
252
        $return .= '</table>';
253
        return $return;
254
    }
255
256
    /**
257
     * Display a sortable table that contains an overview off all the reporting progress of all users and all courses the user is subscribed to
258
     * @author Patrick Cool <[email protected]>, Ghent University, Belgium
259
     * @version Dokeos 1.8.6
260
     * @since October 2008
261
     */
262
    public static function display_tracking_user_overview()
263
    {
264
        MySpace::display_user_overview_export_options();
265
266
        $t_head = '    <table style="width: 100%;border:0;padding:0;border-collapse:collapse;table-layout: fixed">';
267
        //$t_head .= '  <caption>'.get_lang('CourseInformation').'</caption>';
268
        $t_head .=      '<tr>';
269
        $t_head .= '        <th width="155px" style="border-left:0;border-bottom:0"><span>'.get_lang('Course').'</span></th>';
270
        $t_head .= '        <th style="padding:0;border-bottom:0"><span>'.cut(get_lang('AvgTimeSpentInTheCourse'), 6, true).'</span></th>';
271
        $t_head .= '        <th style="padding:0;border-bottom:0"><span>'.cut(get_lang('AvgStudentsProgress'), 6, true).'</span></th>';
272
        $t_head .= '        <th style="padding:0;border-bottom:0"><span>'.cut(get_lang('AvgCourseScore'), 6, true).'</span></th>';
273
        //$t_head .= '      <th><div style="width:40px">'.get_lang('AvgExercisesScore').'</div></th>';
274
        $t_head .= '        <th style="padding:0;border-bottom:0"><span>'.cut(get_lang('TotalNumberOfMessages'), 6, true).'</span></th>';
275
        $t_head .= '        <th style="padding:0;border-bottom:0"><span>'.cut(get_lang('TotalNumberOfAssignments'), 6, true).'</span></th>';
276
        $t_head .= '        <th width="105px" style="border-bottom:0"><span>'.get_lang('TotalExercisesScoreObtained').'</span></th>';
277
        //$t_head .= '      <th><div>'.get_lang('TotalExercisesScorePossible').'</div></th>';
278
        $t_head .= '        <th style="padding:0;border-bottom:0"><span>'.cut(get_lang('TotalExercisesAnswered'), 6, true).'</span></th>';
279
        //$t_head .= '      <th><div>'.get_lang('TotalExercisesScorePercentage').'</div></th>';
280
        //$t_head .= '      <th><div style="width:60px">'.get_lang('FirstLogin').'</div></th>';
281
        $t_head .= '        <th style="padding:0;border-bottom:0;border-right:0;"><span>'.get_lang('LatestLogin').'</span></th>';
282
        $t_head .= '    </tr></table>';
283
284
        $addparams = array('view' => 'admin', 'display' => 'user');
285
286
        $table = new SortableTable('tracking_user_overview', array('MySpace','get_number_of_users_tracking_overview'), array('MySpace','get_user_data_tracking_overview'), 0);
287
        $table->additional_parameters = $addparams;
288
289
        $table->set_header(0, get_lang('OfficialCode'), true, array('style' => 'font-size:8pt'), array('style' => 'font-size:8pt'));
290
        if (api_is_western_name_order()) {
291
            $table->set_header(1, get_lang('FirstName'), true, array('style' => 'font-size:8pt'), array('style' => 'font-size:8pt'));
292
            $table->set_header(2, get_lang('LastName'), true, array('style' => 'font-size:8pt'), array('style' => 'font-size:8pt'));
293
        } else {
294
            $table->set_header(1, get_lang('LastName'), true, array('style' => 'font-size:8pt'), array('style' => 'font-size:8pt'));
295
            $table->set_header(2, get_lang('FirstName'), true, array('style' => 'font-size:8pt'), array('style' => 'font-size:8pt'));
296
        }
297
        $table->set_header(3, get_lang('LoginName'), true, array('style' => 'font-size:8pt'), array('style' => 'font-size:8pt'));
298
        $table->set_header(4, $t_head, false, array('style' => 'width:90%;border:0;padding:0;font-size:7.5pt;'), array('style' => 'width:90%;padding:0;font-size:7.5pt;'));
299
        $table->set_column_filter(4, array('MySpace','course_info_tracking_filter'));
300
        $table->display();
301
    }
302
303
    public static function display_tracking_coach_overview($export_csv)
304
    {
305
        global $charset;
306
307
        if ($export_csv) {
308
            $is_western_name_order = api_is_western_name_order(PERSON_NAME_DATA_EXPORT);
309
        } else {
310
            $is_western_name_order = api_is_western_name_order();
311
        }
312
        $sort_by_first_name = api_sort_by_first_name();
313
        $tracking_column = isset($_GET['tracking_list_coaches_column']) ? $_GET['tracking_list_coaches_column'] : ($is_western_name_order xor $sort_by_first_name) ? 1 : 0;
314
        $tracking_direction = (isset($_GET['tracking_list_coaches_direction']) && in_array(strtoupper($_GET['tracking_list_coaches_direction']), array('ASC', 'DESC', 'ASCENDING', 'DESCENDING', '0', '1'))) ? $_GET['tracking_list_coaches_direction'] : 'DESC';
315
        // Prepare array for column order - when impossible, use some of user names.
316
        if ($is_western_name_order) {
317
            $order = array(0 => 'firstname', 1 => 'lastname', 2 => ($sort_by_first_name ? 'firstname' : 'lastname'), 3 => 'login_date', 4 => ($sort_by_first_name ? 'firstname' : 'lastname'), 5 => ($sort_by_first_name ? 'firstname' : 'lastname'));
318
        } else {
319
            $order = array(0 => 'lastname', 1 => 'firstname', 2 => ($sort_by_first_name ? 'firstname' : 'lastname'), 3 => 'login_date', 4 => ($sort_by_first_name ? 'firstname' : 'lastname'), 5 => ($sort_by_first_name ? 'firstname' : 'lastname'));
320
        }
321
        $table = new SortableTable(
322
            'tracking_list_coaches_myspace',
323
            array('MySpace', 'count_coaches'),
324
            null,
325
            ($is_western_name_order xor $sort_by_first_name) ? 1 : 0
326
        );
327
        $parameters['view'] = 'admin';
328
        $table->set_additional_parameters($parameters);
329 View Code Duplication
        if ($is_western_name_order) {
330
            $table -> set_header(0, get_lang('FirstName'), true);
331
            $table -> set_header(1, get_lang('LastName'), true);
332
        } else {
333
            $table -> set_header(0, get_lang('LastName'), true);
334
            $table -> set_header(1, get_lang('FirstName'), true);
335
        }
336
        $table -> set_header(2, get_lang('TimeSpentOnThePlatform'), false);
337
        $table -> set_header(3, get_lang('LastConnexion'), false);
338
        $table -> set_header(4, get_lang('NbStudents'), false);
339
        $table -> set_header(5, get_lang('CountCours'), false);
340
        $table -> set_header(6, get_lang('NumberOfSessions'), false);
341
        $table -> set_header(7, get_lang('Sessions'), false);
342
343
        if ($is_western_name_order) {
344
            $csv_header[] = array (
345
                get_lang('FirstName', ''),
346
                get_lang('LastName', ''),
347
                get_lang('TimeSpentOnThePlatform', ''),
348
                get_lang('LastConnexion', ''),
349
                get_lang('NbStudents', ''),
350
                get_lang('CountCours', ''),
351
                get_lang('NumberOfSessions', '')
352
            );
353
        } else {
354
            $csv_header[] = array (
355
                get_lang('LastName', ''),
356
                get_lang('FirstName', ''),
357
                get_lang('TimeSpentOnThePlatform', ''),
358
                get_lang('LastConnexion', ''),
359
                get_lang('NbStudents', ''),
360
                get_lang('CountCours', ''),
361
                get_lang('NumberOfSessions', '')
362
            );
363
        }
364
365
        $tbl_track_login = Database :: get_main_table(TABLE_STATISTIC_TRACK_E_LOGIN);
366
        $tbl_user = Database::get_main_table(TABLE_MAIN_USER);
367
        $tbl_session_course_user = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
368
        $tbl_sessions = Database::get_main_table(TABLE_MAIN_SESSION);
369
370
        $sqlCoachs = "SELECT DISTINCT
371
                        scu.user_id as id_coach,
372
                        u.id as user_id,
373
                        lastname,
374
                        firstname,
375
                        MAX(login_date) as login_date
376
                        FROM $tbl_user u, $tbl_session_course_user scu, $tbl_track_login
377
                        WHERE
378
                            scu.user_id = u.id AND scu.status=2 AND login_user_id=u.id
379
                        GROUP BY user_id ";
380
381
        if (api_is_multiple_url_enabled()) {
382
            $tbl_session_rel_access_url = Database::get_main_table(TABLE_MAIN_ACCESS_URL_REL_SESSION);
383
            $access_url_id = api_get_current_access_url_id();
384
            if ($access_url_id != -1) {
385
                $sqlCoachs = "SELECT DISTINCT
386
                                    scu.user_id as id_coach,
387
                                    u.id as user_id,
388
                                    lastname,
389
                                    firstname,
390
                                    MAX(login_date) as login_date
391
                                FROM $tbl_user u,
392
                                $tbl_session_course_user scu,
393
                                $tbl_track_login ,
394
                                $tbl_session_rel_access_url session_rel_url
395
                                WHERE
396
                                    scu.user_id = u.id AND
397
                                    scu.status = 2 AND
398
                                    login_user_id = u.id AND
399
                                    access_url_id = $access_url_id AND
400
                                    session_rel_url.session_id = scu.session_id
401
                                GROUP BY u.id";
402
            }
403
        }
404
        if (!empty($order[$tracking_column])) {
405
            $sqlCoachs .= "ORDER BY ".$order[$tracking_column]." ".$tracking_direction;
406
        }
407
408
        $result_coaches = Database::query($sqlCoachs);
409
        $total_no_coaches = Database::num_rows($result_coaches);
410
        $global_coaches = array();
411
        while ($coach = Database::fetch_array($result_coaches)) {
412
            $global_coaches[$coach['user_id']] = $coach;
413
        }
414
415
        $sql_session_coach = 'SELECT session.id_coach, u.id as user_id, lastname, firstname, MAX(login_date) as login_date
416
                                FROM '.$tbl_user.' u ,'.$tbl_sessions.' as session,'.$tbl_track_login.'
417
                                WHERE id_coach = u.id AND login_user_id = u.id
418
                                GROUP BY u.id
419
                                ORDER BY login_date '.$tracking_direction;
420
421
        if (api_is_multiple_url_enabled()) {
422
            $tbl_session_rel_access_url = Database::get_main_table(TABLE_MAIN_ACCESS_URL_REL_SESSION);
423
            $access_url_id = api_get_current_access_url_id();
424
            if ($access_url_id != -1) {
425
                $sql_session_coach = 'SELECT session.id_coach, u.id as user_id, lastname, firstname, MAX(login_date) as login_date
426
					FROM '.$tbl_user.' u ,'.$tbl_sessions.' as session, '.$tbl_track_login.' , '.$tbl_session_rel_access_url.' as session_rel_url
427
					WHERE
428
					    id_coach = u.id AND
429
					    login_user_id = u.id  AND
430
					    access_url_id = '.$access_url_id.' AND
431
					    session_rel_url.session_id = session.id
432
					GROUP BY  u.id
433
					ORDER BY login_date '.$tracking_direction;
434
            }
435
        }
436
437
        $result_sessions_coach = Database::query($sql_session_coach);
438
        $total_no_coaches += Database::num_rows($result_sessions_coach);
439
        while ($coach = Database::fetch_array($result_sessions_coach)) {
440
            $global_coaches[$coach['user_id']] = $coach;
441
        }
442
443
        $all_datas = array();
444
445
        foreach ($global_coaches as $id_coach => $coaches) {
446
447
            $time_on_platform   = api_time_to_hms(Tracking :: get_time_spent_on_the_platform($coaches['user_id']));
448
            $last_connection    = Tracking :: get_last_connection_date($coaches['user_id']);
449
            $nb_students        = count(Tracking :: get_student_followed_by_coach($coaches['user_id']));
450
            $nb_courses         = count(Tracking :: get_courses_followed_by_coach($coaches['user_id']));
451
            $nb_sessions        = count(Tracking :: get_sessions_coached_by_user($coaches['user_id']));
452
453
            $table_row = array();
454
            if ($is_western_name_order) {
455
                $table_row[] = $coaches['firstname'];
456
                $table_row[] = $coaches['lastname'];
457
            } else {
458
                $table_row[] = $coaches['lastname'];
459
                $table_row[] = $coaches['firstname'];
460
            }
461
            $table_row[] = $time_on_platform;
462
            $table_row[] = $last_connection;
463
            $table_row[] = $nb_students;
464
            $table_row[] = $nb_courses;
465
            $table_row[] = $nb_sessions;
466
            $table_row[] = '<a href="session.php?id_coach='.$coaches['user_id'].'">
467
                '.Display::return_icon('2rightarrow.png').'
468
            </a>';
469
            $all_datas[] = $table_row;
470
471
            if ($is_western_name_order) {
472
                $csv_content[] = array(
473
                    api_html_entity_decode($coaches['firstname'], ENT_QUOTES),
474
                    api_html_entity_decode($coaches['lastname'], ENT_QUOTES),
475
                    $time_on_platform,
476
                    $last_connection,
477
                    $nb_students,
478
                    $nb_courses,
479
                    $nb_sessions
480
                );
481
            } else {
482
                $csv_content[] = array(
483
                    api_html_entity_decode($coaches['lastname'], ENT_QUOTES),
484
                    api_html_entity_decode($coaches['firstname'], ENT_QUOTES),
485
                    $time_on_platform,
486
                    $last_connection,
487
                    $nb_students,
488
                    $nb_courses,
489
                    $nb_sessions
490
                );
491
            }
492
        }
493
494
        if ($tracking_column != 3) {
495
            if ($tracking_direction == 'DESC') {
496
                usort($all_datas, array('MySpace','rsort_users'));
497
            } else {
498
                usort($all_datas, array('MySpace','sort_users'));
499
            }
500
        }
501
502
        if ($export_csv && $tracking_column != 3) {
503
            usort($csv_content, 'sort_users');
504
        }
505
        if ($export_csv) {
506
            $csv_content = array_merge($csv_header, $csv_content);
507
        }
508
509
        foreach ($all_datas as $row) {
510
            $table -> addRow($row, 'align="right"');
511
        }
512
        $table -> display();
513
    }
514
515
    public static function count_coaches() {
516
        global $total_no_coaches;
517
        return $total_no_coaches;
518
    }
519
520
    public static function sort_users($a, $b) {
521
        return api_strcmp(trim(api_strtolower($a[$_SESSION['tracking_column']])), trim(api_strtolower($b[$_SESSION['tracking_column']])));
522
    }
523
524
    public static function rsort_users($a, $b) {
525
        return api_strcmp(trim(api_strtolower($b[$_SESSION['tracking_column']])), trim(api_strtolower($a[$_SESSION['tracking_column']])));
526
    }
527
528
    /**
529
     * Display a sortable table that contains an overview off all the progress of the user in a session
530
     * @author César Perales <[email protected]>, Beeznest Team
531
     */
532
    public static function display_tracking_lp_progress_overview($sessionId = '', $courseId = '', $date_from, $date_to)
533
    {
534
        $course = api_get_course_info_by_id($courseId);
535
        /**
536
         * Column name
537
         * The order is important you need to check the $column variable in the model.ajax.php file
538
         */
539
        $columns = array(
540
            get_lang('Username'),
541
            get_lang('FirstName'),
542
            get_lang('LastName'),
543
        );
544
        //add lessons of course
545
        $lessons = LearnpathList::get_course_lessons($course['code'], $sessionId);
546
547
        //create columns array
548
        foreach ($lessons as $lesson_id => $lesson) {
549
            $columns[] = $lesson['name'];
550
        }
551
552
        $columns[] = get_lang('Total');
553
554
        /**
555
         * Column config
556
         */
557
        $column_model   = array(
558
            array(
559
                'name' => 'username',
560
                'index' => 'username',
561
                'align' => 'left',
562
                'search' => 'true',
563
                'wrap_cell' => "true",
564
            ),
565
            array(
566
                'name' => 'firstname',
567
                'index' => 'firstname',
568
                'align' => 'left',
569
                'search' => 'true',
570
            ),
571
            array(
572
                'name' => 'lastname',
573
                'index' => 'lastname',
574
                'align' => 'left',
575
                'search' => 'true',
576
            ),
577
        );
578
579
        // Get dinamic column names
580
        foreach ($lessons as $lesson_id => $lesson) {
581
            $column_model[] = array(
582
                'name' => $lesson['id'],
583
                'index' => $lesson['id'],
584
                'align' => 'left',
585
                'search' => 'true',
586
            );
587
        }
588
589
        $column_model[] = array(
590
            'name' => 'total',
591
            'index' => 'total',
592
            'align' => 'left',
593
            'search' => 'true',
594
        );
595
596
        $action_links = '';
597
        // jqgrid will use this URL to do the selects
598
        $url = api_get_path(WEB_AJAX_PATH).'model.ajax.php?a=get_session_lp_progress&session_id=' . $sessionId . '&course_id=' . $courseId . '&date_to=' . $date_to . '&date_from=' . $date_from;
599
600
        //Table Id
601
        $tableId = 'lpProgress';
602
603
        //Autowidth
604
        $extra_params['autowidth'] = 'true';
605
606
        //height auto
607
        $extra_params['height'] = 'auto';
608
609
        $table = Display::grid_js(
610
            $tableId,
611
            $url,
612
            $columns,
613
            $column_model,
614
            $extra_params,
615
            array(),
616
            $action_links,
617
            true
618
        );
619
620
        $return = '<script>$(function() {'. $table .
621
            'jQuery("#'.$tableId.'").jqGrid("navGrid","#'.$tableId.'_pager",{view:false, edit:false, add:false, del:false, search:false, excel:true});
622
                jQuery("#'.$tableId.'").jqGrid("navButtonAdd","#'.$tableId.'_pager",{
623
                       caption:"",
624
                       title:"' . get_lang('ExportExcel') . '",
625
                       onClickButton : function () {
626
                           jQuery("#'.$tableId.'").jqGrid("excelExport",{"url":"'.$url.'&export_format=xls"});
627
                       }
628
                });
629
            });</script>';
630
        $return .= Display::grid_html($tableId);
631
        return $return;
632
    }
633
634
    /**
635
     * Display a sortable table that contains an overview off all the progress of the user in a session
636
     * @param   int $sessionId  The session ID
637
     * @param   int $courseId   The course ID
638
     * @param   int $exerciseId The quiz ID
639
     * @param   int $answer Answer status (0 = incorrect, 1 = correct, 2 = both)
0 ignored issues
show
Bug introduced by
There is no parameter named $answer. Was it maybe removed?

This check looks for PHPDoc comments describing methods or function parameters that do not exist on the corresponding method or function.

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

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

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

Loading history...
640
     * @return  string  HTML array of results formatted for gridJS
641
     * @author César Perales <[email protected]>, Beeznest Team
642
     */
643
    static function display_tracking_exercise_progress_overview(
644
        $sessionId = 0,
645
        $courseId = 0,
646
        $exerciseId = 0,
647
        $date_from = null,
648
        $date_to = null
649
    ) {
650
        $date_from = Security::remove_XSS($date_from);
651
        $date_to = Security::remove_XSS($date_to);
652
        /**
653
         * Column names
654
         * The column order is important. Check $column variable in the main/inc/ajax/model.ajax.php file
655
         */
656
        $columns = array(
657
            get_lang('Session'),
658
            get_lang('ExerciseId'),
659
            get_lang('ExerciseName'),
660
            get_lang('Username'),
661
            get_lang('LastName'),
662
            get_lang('FirstName'),
663
            get_lang('Time'),
664
            get_lang('QuestionId'),
665
            get_lang('QuestionTitle'),
666
            get_lang('WorkDescription'),
667
            get_lang('Answer'),
668
            get_lang('Correct'),
669
        );
670
671
        /**
672
         * Column config
673
         */
674
        $column_model   = array(
675
            array('name'=>'session', 'index'=>'session', 'align'=>'left', 'search' => 'true', 'wrap_cell' => "true"),
676
            array('name'=>'exercise_id', 'index'=>'exercise_id', 'align'=>'left', 'search' => 'true'),
677
            array('name'=>'quiz_title', 'index'=>'quiz_title', 'align'=>'left', 'search' => 'true'),
678
            array('name'=>'username', 'index'=>'username', 'align'=>'left', 'search' => 'true'),
679
            array('name'=>'lastname', 'index'=>'lastname', 'align'=>'left', 'search' => 'true'),
680
            array('name'=>'firstname', 'index'=>'firstname', 'align'=>'left', 'search' => 'true'),
681
            array('name'=>'time', 'index'=>'time', 'align'=>'left', 'search' => 'true', 'wrap_cell' => "true"),
682
            array('name'=>'question_id', 'index'=>'question_id', 'align'=>'left', 'search' => 'true'),
683
            array('name'=>'question', 'index'=>'question', 'align'=>'left', 'search' => 'true', 'wrap_cell' => "true"),
684
            array('name'=>'description', 'index'=>'description', 'align'=>'left', 'width' => '550', 'search' => 'true', 'wrap_cell' => "true"),
685
            array('name'=>'answer', 'index'=>'answer', 'align'=>'left', 'search' => 'true', 'wrap_cell' => "true"),
686
            array('name'=>'correct', 'index'=>'correct', 'align'=>'left', 'search' => 'true', 'wrap_cell' => "true"),
687
        );
688
        //get dynamic column names
689
690
        // jqgrid will use this URL to do the selects
691
        $url = api_get_path(WEB_AJAX_PATH).'model.ajax.php?a=get_exercise_progress&session_id=' . $sessionId . '&course_id=' . $courseId  . '&exercise_id=' . $exerciseId . '&date_to=' . $date_to . '&date_from=' . $date_from;
692
693
        // Autowidth
694
        $extra_params['autowidth'] = 'true';
695
696
        // height auto
697
        $extra_params['height'] = 'auto';
698
699
        $tableId = 'exerciseProgressOverview';
700
        $table = Display::grid_js($tableId, $url, $columns, $column_model, $extra_params, array(), '', true);
701
702
        $return = '<script>$(function() {'. $table .
703
            'jQuery("#'.$tableId.'").jqGrid("navGrid","#'.$tableId.'_pager",{view:false, edit:false, add:false, del:false, search:false, excel:true});
704
                jQuery("#'.$tableId.'").jqGrid("navButtonAdd","#'.$tableId.'_pager",{
705
                       caption:"",
706
                       title:"' . get_lang('ExportExcel') . '",
707
                       onClickButton : function () {
708
                           jQuery("#'.$tableId.'").jqGrid("excelExport",{"url":"'.$url.'&export_format=xls"});
709
                       }
710
                });
711
            });</script>';
712
        $return .= Display::grid_html($tableId);
713
        return $return;
714
    }
715
716
    /**
717
     * Display a sortable table that contains an overview off all the progress of the user in a session
718
     * @param   int $sessionId The session ID
719
     * @param   int $courseId The course ID
720
     * @param null $date_from
721
     * @param null $date_to
722
     * @internal param int $exerciseId The quiz ID
723
     * @internal param int $answer Answer status (0 = incorrect, 1 = correct, 2 = both)
724
     * @return  string  HTML array of results formatted for gridJS
725
     * @author Francis Gonzales <[email protected]>, Beeznest Team
726
     */
727
    static function display_tracking_grade_overview($sessionId = 0, $courseId = 0, $date_from = null, $date_to = null)
728
    {
729
        /**
730
         * Column names
731
         * The column order is important. Check $column variable in the main/inc/ajax/model.ajax.php file
732
         */
733
        $objExercise = new Exercise();
734
        $exercises = $objExercise->getExercisesByCouseSession($courseId, $sessionId);
735
736
        $cntExer = 4;
737
        if (!empty($exercises)) {
738
            $cntExer += count($exercises);
739
        }
740
741
        $column = array();
742
        $column_model = array();
743
        $i = 1;
744
        //Get dynamic column names
745
        foreach (range(1, $cntExer) as $cnt) {
746
            switch ($cnt) {
747 View Code Duplication
                case 1:
748
                    $column[] = get_lang('Section');
749
                    $column_model[] = array(
750
                        'name' => 'session',
751
                        'index' => 'session',
752
                        'align' => 'center',
753
                        'search' => 'true',
754
                    );
755
                    break;
756 View Code Duplication
                case 2:
757
                    $column[] = get_lang('Username');
758
                    $column_model[] = array(
759
                        'name' => 'username',
760
                        'index' => 'username',
761
                        'align' => 'center',
762
                        'search' => 'true',
763
                    );
764
                    break;
765 View Code Duplication
                case 3:
766
                    $column[] = get_lang('FirstName');
767
                    $column_model[] = array(
768
                        'name' => 'name',
769
                        'index' => 'name',
770
                        'align' => 'left',
771
                        'search' => 'true',
772
                    );
773
                    break;
774 View Code Duplication
                case $cntExer:
775
                    $column[] = get_lang('FinalScore');
776
                    $column_model[] = array(
777
                        'name' => 'finalscore',
778
                        'index' => 'finalscore',
779
                        'align' => 'center',
780
                        'search' => 'true',
781
                        'wrap_cell' => "true"
782
                    );
783
                    break;
784
                default:
785
                    $title = "";
786 View Code Duplication
                    if (!empty($exercises[$cnt - 4]['title'])) {
787
                        $title = ucwords(strtolower(trim($exercises[$cnt - 4]['title'])));
788
                    }
789
790
                    $column[] = $title;
791
                    $column_model[] = array(
792
                        'name' => 'exer' . $i,
793
                        'index' => 'exer' . $i,
794
                        'align' => 'center',
795
                        'search' => 'true',
796
                        'wrap_cell' => "true"
797
                    );
798
                    $i++;
799
                    break;
800
            }
801
        }
802
803
        //end get dynamic column names
804
        // jqgrid will use this URL to do the selects
805
        $url = api_get_path(WEB_AJAX_PATH) . 'model.ajax.php?a=get_exercise_grade&session_id=' . $sessionId . '&course_id=' . $courseId;
806
807
        // Autowidth
808
        $extra_params['autowidth'] = 'true';
809
810
        // height auto
811
        $extra_params['height'] = 'auto';
812
813
        $tableId = 'exerciseGradeOverview';
814
        $table = Display::grid_js($tableId, $url, $column, $column_model, $extra_params, array(), '', true);
815
816
        $return = '<script>$(function() {' . $table .
817
            'jQuery("#' . $tableId . '").jqGrid("navGrid","#' . $tableId . '_pager",{view:false, edit:false, add:false, del:false, search:false, excel:true});
818
                jQuery("#' . $tableId . '").jqGrid("navButtonAdd","#' . $tableId . '_pager",{
819
                       caption:"",
820
                       title:"' . get_lang('ExportExcel') . '",
821
                       onClickButton : function () {
822
                           jQuery("#' . $tableId . '").jqGrid("excelExport",{"url":"' . $url . '&export_format=xls"});
823
                       }
824
                });
825
            });</script>';
826
        $return .= Display::grid_html($tableId);
827
        return $return;
828
    }
829
830
    /**
831
     * Display a sortable table that contains an overview off all the progress of the user in a session
832
     * @author César Perales <[email protected]>, Beeznest Team
833
     */
834
    function display_survey_overview($sessionId = 0, $courseId = 0, $surveyId = 0, $date_from, $date_to)
835
    {
836
        /**
837
         * Column name
838
         * The order is important you need to check the $column variable in the model.ajax.php file
839
         */
840
        $columns = array(
841
            get_lang('Username'),
842
            get_lang('FirstName'),
843
            get_lang('LastName'),
844
        );
845
        //add lessons of course
846
        $questions = SurveyManager::get_questions($surveyId, $courseId);
847
848
        foreach ($questions as $question) {
849
            $columns[] = $question['question'];
850
        }
851
852
        /**
853
         * Column config
854
         */
855
        $column_model   = array(
856
            array('name'=>'username',   'index'=>'username',    'align'=>'left', 'search' => 'true', 'wrap_cell' => "true"),
857
            array('name'=>'firstname',  'index'=>'firstname',   'align'=>'left', 'search' => 'true'),
858
            array('name'=>'lastname',   'index'=>'lastname',    'align'=>'left', 'search' => 'true'),
859
        );
860
        //get dinamic column names
861
        foreach ($questions as $question_id => $question) {
862
            $column_model[] = array(
863
                'name'=> $question_id,
864
                'index'=>$question_id,
865
                'width'=>'70',
866
                'align'=>'left',
867
                'search' => 'true'
868
            );
869
        }
870
871
        $action_links = '';
872
873
        // jqgrid will use this URL to do the selects
874
        $url = api_get_path(WEB_AJAX_PATH).'model.ajax.php?a=get_survey_overview&session_id=' . $sessionId . '&course_id=' . $courseId . '&survey_id=' . $surveyId . '&date_to=' . $date_to . '&date_from=' . $date_from;
875
876
        // Table Id
877
        $tableId = 'lpProgress';
878
879
        //Autowidth
880
        $extra_params['autowidth'] = 'true';
881
882
        // height auto
883
        $extra_params['height'] = 'auto';
884
885
        $table = Display::grid_js(
886
            $tableId,
887
            $url,
888
            $columns,
889
            $column_model,
890
            $extra_params,
891
            array(),
892
            $action_links,
893
            true
894
        );
895
896
        $return = '<script>$(function() {'. $table .
897
            'jQuery("#'.$tableId.'").jqGrid("navGrid","#'.$tableId.'_pager",{view:false, edit:false, add:false, del:false, search:false, excel:true});
898
                jQuery("#'.$tableId.'").jqGrid("navButtonAdd","#'.$tableId.'_pager",{
899
                       caption:"",
900
                       title:"' . get_lang('ExportExcel') . '",
901
                       onClickButton : function () {
902
                           jQuery("#'.$tableId.'").jqGrid("excelExport",{"url":"'.$url.'&export_format=xls"});
903
                       }
904
                });
905
            });</script>';
906
        $return .= Display::grid_html($tableId);
907
908
        return $return;
909
    }
910
911
    /**
912
     * Display a sortable table that contains an overview off all the progress of the user in a session
913
     * @author César Perales <[email protected]>, Beeznest Team
914
     */
915
    static function display_tracking_progress_overview($sessionId = 0, $courseId = 0,  $date_from, $date_to)
916
    {
917
        //The order is important you need to check the the $column variable in the model.ajax.php file
918
        $columns = array(
919
            get_lang('LastName'),
920
            get_lang('FirstName'),
921
            get_lang('Username'),
922
            #get_lang('Profile'),
923
            get_lang('Total'),
924
            get_lang('Courses'),
925
            get_lang('LearningPaths'),
926
            get_lang('Exercises'),
927
            get_lang('Forums'),
928
            get_lang('Assignments'),
929
            get_lang('ToolWiki'),
930
            get_lang('ToolSurvey'),
931
            //Learning paths
932
            get_lang('LearnpathsTotal'),
933
            get_lang('LearnpathsDone'),
934
            get_lang('LearnpathsLeft'),
935
            get_lang('LearnpathsProgress'),
936
            //Exercises
937
            get_lang('ExercisesTotal'),
938
            get_lang('ExercisesDone'),
939
            get_lang('ExercisesLeft'),
940
            get_lang('ExercisesProgress'),
941
            //Forums
942
            get_lang('ForumsTotal'),
943
            get_lang('ForumsDone'),
944
            get_lang('ForumsLeft'),
945
            get_lang('ForumsProgress'),
946
            //Assignments
947
            get_lang('AssignmentsTotal'),
948
            get_lang('AssignmentsDone'),
949
            get_lang('AssignmentsLeft'),
950
            get_lang('AssignmentsProgress'),
951
            //Wiki
952
            get_lang('WikiTotal'),
953
            get_lang('WikiRevisions'),
954
            get_lang('WikiRead'),
955
            get_lang('WikiUnread'),
956
            get_lang('WikiProgress'),
957
            //Surveys
958
            get_lang('SurveysTotal'),
959
            get_lang('SurveysDone'),
960
            get_lang('SurveysLeft'),
961
            get_lang('SurveysProgress'),
962
        );
963
964
        //Column config
965
        $column_model   = array(
966
            array('name'=>'lastname',   'index'=>'lastname',     'align'=>'left'),
967
            array('name'=>'firstname',  'index'=>'firstname',    'align'=>'left'),
968
            array('name'=>'username',   'index'=>'username',     'align'=>'left'),
969
            #array('name'=>'profile',   'index'=>'username',     'align'=>'left'),
970
            array('name'=>'total',      'index'=>'total',        'align'=>'left'),
971
            array('name'=>'courses',    'index'=>'courses',      'align'=>'left', 'sortable' => 'false'),
972
            array('name'=>'lessons',    'index'=>'lessons',      'align'=>'left', 'sortable' => 'false'),
973
            array('name'=>'exercises',  'index'=>'exercises',    'align'=>'left', 'sortable' => 'false'),
974
            array('name'=>'forums',     'index'=>'forums',       'align'=>'left', 'sortable' => 'false'),
975
            array('name'=>'homeworks',  'index'=>'homeworks',    'align'=>'left', 'sortable' => 'false'),
976
            array('name'=>'wikis',      'index'=>'wikis',        'align'=>'left', 'sortable' => 'false'),
977
            array('name'=>'surveys',    'index'=>'surveys',      'align'=>'left', 'sortable' => 'false'),
978
            //Lessons
979
            array('name'=>'lessons_total',    'index'=>'lessons_total',      'align'=>'center', 'sortable' => 'false'),
980
            array('name'=>'lessons_done',     'index'=>'lessons_done',       'align'=>'center', 'sortable' => 'false'),
981
            array('name'=>'lessons_left',     'index'=>'lessons_left',       'align'=>'center', 'sortable' => 'false'),
982
            array('name'=>'lessons_progress', 'index'=>'lessons_progress',   'align'=>'center', 'sortable' => 'false'),
983
            //Exercises
984
            array('name'=>'exercises_total',    'index'=>'exercises_total',      'align'=>'center', 'sortable' => 'false'),
985
            array('name'=>'exercises_done',     'index'=>'exercises_done',       'align'=>'center', 'sortable' => 'false'),
986
            array('name'=>'exercises_left',     'index'=>'exercises_left',       'align'=>'center', 'sortable' => 'false'),
987
            array('name'=>'exercises_progress', 'index'=>'exercises_progress',   'align'=>'center', 'sortable' => 'false'),
988
            //Assignments
989
            array('name'=>'forums_total',    'index'=>'forums_total',        'align'=>'center', 'sortable' => 'false'),
990
            array('name'=>'forums_done',     'index'=>'forums_done',         'align'=>'center', 'sortable' => 'false'),
991
            array('name'=>'forums_left',     'index'=>'forums_left',         'align'=>'center', 'sortable' => 'false'),
992
            array('name'=>'forums_progress', 'index'=>'forums_progress',     'align'=>'center', 'sortable' => 'false'),
993
            //Assignments
994
            array('name'=>'assigments_total',    'index'=>'assigments_total',        'align'=>'center', 'sortable' => 'false'),
995
            array('name'=>'assigments_done',     'index'=>'assigments_done',         'align'=>'center', 'sortable' => 'false'),
996
            array('name'=>'assigments_left',     'index'=>'assigments_left',         'align'=>'center', 'sortable' => 'false'),
997
            array('name'=>'assigments_progress', 'index'=>'assigments_progress',     'align'=>'center', 'sortable' => 'false'),
998
            //Assignments
999
            array('name'=>'wiki_total',         'index'=>'wiki_total',       'align'=>'center', 'sortable' => 'false'),
1000
            array('name'=>'wiki_revisions',     'index'=>'wiki_revisions',   'align'=>'center', 'sortable' => 'false'),
1001
            array('name'=>'wiki_read',          'index'=>'wiki_read',        'align'=>'center', 'sortable' => 'false'),
1002
            array('name'=>'wiki_unread',        'index'=>'wiki_unread',      'align'=>'center', 'sortable' => 'false'),
1003
            array('name'=>'wiki_progress',      'index'=>'wiki_progress',    'align'=>'center', 'sortable' => 'false'),
1004
            //Surveys
1005
            array('name'=>'surveys_total',    'index'=>'surveys_total',      'align'=>'center', 'sortable' => 'false'),
1006
            array('name'=>'surveys_done',     'index'=>'surveys_done',       'align'=>'center', 'sortable' => 'false'),
1007
            array('name'=>'surveys_left',     'index'=>'surveys_left',       'align'=>'center', 'sortable' => 'false'),
1008
            array('name'=>'surveys_progress', 'index'=>'surveys_progress',   'align'=>'center', 'sortable' => 'false'),
1009
        );
1010
1011
        $action_links = '';
1012
        // jqgrid will use this URL to do the selects
1013
        $url = api_get_path(WEB_AJAX_PATH).'model.ajax.php?a=get_session_progress&session_id=' . $sessionId . '&course_id=' . $courseId . '&date_to=' . $date_to . '&date_from=' . $date_from;
1014
1015
        //Table Id
1016
        $tableId = 'progressOverview';
1017
1018
        //Autowidth
1019
        $extra_params['autowidth'] = 'true';
1020
        $extra_params['shrinkToFit'] = 'true';
1021
        $extra_params['headertitles'] = 'true';
1022
        $extra_params['groupHeaders'] = array(
1023
            'courses_detail' => array(
1024
                "startColumnName" => 'courses',
1025
                "numberOfColumns" => 7,
1026
                "titleText" => get_lang('Global'),
1027
            ),
1028
            'lessons' => array(
1029
                "startColumnName" => 'lessons_total',
1030
                "numberOfColumns" => 4,
1031
                "titleText" => get_lang('LearningPaths'),
1032
            ),
1033
            'exercises' => array(
1034
                "startColumnName" => 'exercises_total',
1035
                "numberOfColumns" => 4,
1036
                "titleText" => get_lang('Exercises'),
1037
            ),
1038
            'forums' => array(
1039
                "startColumnName" => 'forums_total',
1040
                "numberOfColumns" => 4,
1041
                "titleText" => get_lang('Forums'),
1042
            ),
1043
            'assignments' => array(
1044
                "startColumnName" => 'assigments_total',
1045
                "numberOfColumns" => 4,
1046
                "titleText" => get_lang('Assignments'),
1047
            ),
1048
            'wikis' => array(
1049
                "startColumnName" => 'wiki_total',
1050
                "numberOfColumns" => 5,
1051
                "titleText" => get_lang('Wiki'),
1052
            ),
1053
            'surveys' => array(
1054
                "startColumnName" => 'surveys_total',
1055
                "numberOfColumns" => 4,
1056
                "titleText" => get_lang('Survey'),
1057
            ),
1058
        );
1059
        //height auto
1060
        $extra_params['height'] = 'auto';
1061
1062
        $table = Display::grid_js(
1063
            $tableId,
1064
            $url,
1065
            $columns,
1066
            $column_model,
1067
            $extra_params,
1068
            array(),
1069
            $action_links,
1070
            true
1071
        );
1072
1073
        $return = '<script>$(function() {'. $table .
1074
            'jQuery("#'.$tableId.'").jqGrid("navGrid","#'.$tableId.'_pager",{view:false, edit:false, add:false, del:false, search:false, excel:true});
1075
                jQuery("#'.$tableId.'").jqGrid("navButtonAdd","#'.$tableId.'_pager",{
1076
                       caption:"",
1077
                       title:"' . get_lang('ExportExcel') . '",
1078
                       onClickButton : function () {
1079
                           jQuery("#'.$tableId.'").jqGrid("excelExport",{"url":"'.$url.'&export_format=xls"});
1080
                       }
1081
                });
1082
            });</script>';
1083
        $return .= Display::grid_html($tableId);
1084
        return $return;
1085
    }
1086
1087
    /**
1088
     * Displays a form with all the additionally defined user fields of the profile
1089
     * and give you the opportunity to include these in the CSV export
1090
     *
1091
     * @author Patrick Cool <[email protected]>, Ghent University, Belgium
1092
     * @version 1.8.6
1093
     * @since November 2008
1094
     */
1095
    public static function display_user_overview_export_options()
1096
    {
1097
        $message = '';
1098
        // include the user manager and formvalidator library
1099
        if (isset($_GET['export']) && $_GET['export'] == 'options') {
1100
            // get all the defined extra fields
1101
            $extrafields = UserManager::get_extra_fields(0, 50, 5, 'ASC', false, 1);
1102
1103
            // creating the form with all the defined extra fields
1104
            $form = new FormValidator(
1105
                'exportextrafields',
1106
                'post',
1107
                api_get_self()."?view=".Security::remove_XSS($_GET['view']).'&display='.Security::remove_XSS($_GET['display']).'&export='.Security::remove_XSS($_GET['export'])
1108
            );
1109
1110
            if (is_array($extrafields) && count($extrafields) > 0) {
1111
                foreach ($extrafields as $key => $extra) {
1112
                    $form->addElement('checkbox', 'extra_export_field'.$extra[0], '', $extra[3]);
1113
                }
1114
                $form->addButtonSave(get_lang('Ok'), 'submit');
1115
1116
                // setting the default values for the form that contains all the extra fields
1117
                if (is_array($_SESSION['additional_export_fields'])) {
1118
                    foreach ($_SESSION['additional_export_fields'] as $key => $value) {
1119
                        $defaults['extra_export_field'.$value] = 1;
1120
                    }
1121
                }
1122
                $form->setDefaults($defaults);
1123
            } else {
1124
                $form->addElement('html', Display::display_warning_message(get_lang('ThereAreNotExtrafieldsAvailable')));
1125
            }
1126
1127
            if ($form->validate()) {
1128
                // exporting the form values
1129
                $values = $form->exportValues();
1130
1131
                // re-initialising the session that contains the additional fields that need to be exported
1132
                $_SESSION['additional_export_fields'] = array();
1133
1134
                // adding the fields that are checked to the session
1135
                $message = '';
1136
                foreach ($values as $field_ids => $value) {
1137
                    if ($value == 1 && strstr($field_ids,'extra_export_field')) {
1138
                        $_SESSION['additional_export_fields'][] = str_replace('extra_export_field', '', $field_ids);
1139
                    }
1140
                }
1141
1142
                // adding the fields that will be also exported to a message string
1143
                if (is_array($_SESSION['additional_export_fields'])) {
1144 View Code Duplication
                    foreach ($_SESSION['additional_export_fields'] as $key => $extra_field_export) {
1145
                        $message .= '<li>'.$extrafields[$extra_field_export][3].'</li>';
1146
                    }
1147
                }
1148
1149
                // Displaying a feedback message
1150
                if (!empty($_SESSION['additional_export_fields'])) {
1151
                    Display::display_confirmation_message(get_lang('FollowingFieldsWillAlsoBeExported').': <br /><ul>'.$message.'</ul>', false);
1152
                } else  {
1153
                    Display::display_confirmation_message(get_lang('NoAdditionalFieldsWillBeExported'), false);
1154
                }
1155
            } else {
1156
                $form->display();
1157
            }
1158
1159
        } else {
1160
            if (!empty($_SESSION['additional_export_fields'])) {
1161
                // get all the defined extra fields
1162
                $extrafields = UserManager::get_extra_fields(0, 50, 5, 'ASC');
1163
1164 View Code Duplication
                foreach ($_SESSION['additional_export_fields'] as $key => $extra_field_export) {
1165
                    $message .= '<li>'.$extrafields[$extra_field_export][3].'</li>';
1166
                }
1167
1168
                Display::display_normal_message(get_lang('FollowingFieldsWillAlsoBeExported').': <br /><ul>'.$message.'</ul>', false);
1169
            }
1170
        }
1171
    }
1172
1173
    /**
1174
     * Display a sortable table that contains an overview of all the reporting progress of all courses
1175
     */
1176
    public static function display_tracking_course_overview()
1177
    {
1178
        $t_head = '    <table style="width: 100%;border:0;padding:0;border-collapse:collapse;table-layout: fixed">';
1179
        //$t_head .= '  <caption>'.get_lang('CourseInformation').'</caption>';
1180
        $t_head .=      '<tr>';
1181
        $t_head .= '        <th style="padding:0;border-bottom:0"><span>'.cut(get_lang('AvgTimeSpentInTheCourse'), 6, true).'</span></th>';
1182
        $t_head .= '        <th style="padding:0;border-bottom:0"><span>'.cut(get_lang('AvgStudentsProgress'), 6, true).'</span></th>';
1183
        $t_head .= '        <th style="padding:0;border-bottom:0"><span>'.cut(get_lang('AvgCourseScore'), 6, true).'</span></th>';
1184
        //$t_head .= '      <th><div style="width:40px">'.get_lang('AvgExercisesScore').'</div></th>';
1185
        $t_head .= '        <th style="padding:0;border-bottom:0"><span>'.cut(get_lang('TotalNumberOfMessages'), 6, true).'</span></th>';
1186
        $t_head .= '        <th style="padding:0;border-bottom:0"><span>'.cut(get_lang('TotalNumberOfAssignments'), 6, true).'</span></th>';
1187
        $t_head .= '        <th width="105px" style="border-bottom:0"><span>'.get_lang('TotalExercisesScoreObtained').'</span></th>';
1188
        //$t_head .= '      <th><div>'.get_lang('TotalExercisesScorePossible').'</div></th>';
1189
        $t_head .= '        <th style="padding:0;border-bottom:0"><span>'.cut(get_lang('TotalExercisesAnswered'), 6, true).'</span></th>';
1190
        //$t_head .= '      <th><div>'.get_lang('TotalExercisesScorePercentage').'</div></th>';
1191
        //$t_head .= '      <th><div style="width:60px">'.get_lang('FirstLogin').'</div></th>';
1192
        $t_head .= '        <th style="padding:0;border-bottom:0;border-right:0;"><span>'.get_lang('LatestLogin').'</span></th>';
1193
        $t_head .= '    </tr></table>';
1194
1195
        $addparams = array('view' => 'admin', 'display' => 'courseoverview');
1196
1197
        $table = new SortableTable('tracking_session_overview', array('MySpace', 'get_total_number_courses'), array('MySpace','get_course_data_tracking_overview'), 1);
1198
        $table->additional_parameters = $addparams;
1199
1200
        $table->set_header(0, '', false, null, array('style' => 'display: none'));
1201
        $table->set_header(1, get_lang('Course'), true, array('style' => 'font-size:8pt'), array('style' => 'font-size:8pt'));
1202
        $table->set_header(2, $t_head, false, array('style' => 'width:90%;border:0;padding:0;font-size:7.5pt;'), array('style' => 'width:90%;padding:0;font-size:7.5pt;'));
1203
        $table->set_column_filter(2, array('MySpace','course_tracking_filter'));
1204
        $table->display();
1205
    }
1206
1207
    /**
1208
     * Get the total number of courses
1209
     *
1210
     * @return integer Total number of courses
1211
     */
1212
    public static function get_total_number_courses()
1213
    {
1214
        // database table definition
1215
        $main_course_table = Database :: get_main_table(TABLE_MAIN_COURSE);
1216
1217
        return Database::count_rows($main_course_table);
0 ignored issues
show
Deprecated Code introduced by
The method Database::count_rows() has been deprecated.

This method has been deprecated.

Loading history...
1218
    }
1219
1220
    /**
1221
     * Get data for the courses
1222
     *
1223
     * @param int Inferior limit
1224
     * @param int Number of items to select
1225
     * @param string Column to order on
1226
     * @param string Order direction
1227
     * @return array Results
1228
     */
1229 View Code Duplication
    public static function get_course_data_tracking_overview($from, $number_of_items, $column, $direction)
1230
    {
1231
        $main_course_table = Database :: get_main_table(TABLE_MAIN_COURSE);
1232
        $from = intval($from);
1233
        $number_of_items = intval($number_of_items);
1234
1235
        $sql = "SELECT code AS col0, title AS col1 FROM $main_course_table";
1236
        $sql .= " ORDER BY col$column $direction ";
1237
        $sql .= " LIMIT $from,$number_of_items";
1238
        $result = Database::query($sql);
1239
        $return = array ();
1240
        while ($course = Database::fetch_row($result)) {
1241
            $return[] = $course;
1242
        }
1243
        return $return;
1244
    }
1245
1246
    /**
1247
     * Fills in course reporting data
1248
     *
1249
     * @param integer course code
1250
     * @param array $url_params additional url parameters
1251
     * @param array $row the row information (the other columns)
1252
     * @return string html code
1253
     */
1254
    public static function course_tracking_filter($course_code, $url_params, $row)
1255
    {
1256
        $course_code = $row[0];
1257
        $courseInfo = api_get_course_info($course_code);
1258
        $courseId = $courseInfo['real_id'];
1259
1260
        // the table header
1261
        $return = '<table class="data_table" style="width: 100%;border:0;padding:0;border-collapse:collapse;table-layout: fixed">';
1262
1263
        // database table definition
1264
        $tbl_course_rel_user = Database :: get_main_table(TABLE_MAIN_COURSE_USER);
1265
        $tbl_user = Database :: get_main_table(TABLE_MAIN_USER);
1266
1267
        // getting all the courses of the user
1268
        $sql = "SELECT *
1269
                FROM $tbl_user AS u
1270
                INNER JOIN $tbl_course_rel_user AS cu
1271
                ON cu.user_id = u.user_id
1272
                WHERE cu.c_id = '".$courseId."'";
1273
        $result = Database::query($sql);
1274
        $time_spent = 0;
1275
        $progress = 0;
1276
        $nb_progress_lp = 0;
1277
        $score = 0;
1278
        $nb_score_lp = 0;
1279
        $nb_messages = 0;
1280
        $nb_assignments = 0;
1281
        $last_login_date = false;
1282
        $total_score_obtained = 0;
1283
        $total_score_possible = 0;
1284
        $total_questions_answered = 0;
1285 View Code Duplication
        while ($row = Database::fetch_object($result)) {
1286
            // get time spent in the course and session
1287
            $time_spent += Tracking::get_time_spent_on_the_course($row->user_id, $courseInfo['real_id']);
1288
            $progress_tmp = Tracking::get_avg_student_progress($row->user_id, $course_code, array(), null, true);
1289
            $progress += $progress_tmp[0];
1290
            $nb_progress_lp += $progress_tmp[1];
1291
            $score_tmp = Tracking :: get_avg_student_score($row->user_id, $course_code, array(), null, true);
1292
            if(is_array($score_tmp)) {
1293
                $score += $score_tmp[0];
1294
                $nb_score_lp += $score_tmp[1];
1295
            }
1296
            $nb_messages += Tracking::count_student_messages($row->user_id, $course_code);
1297
            $nb_assignments += Tracking::count_student_assignments($row->user_id, $course_code);
1298
            $last_login_date_tmp = Tracking :: get_last_connection_date_on_the_course($row->user_id, $courseInfo, null, false);
1299
            if($last_login_date_tmp != false && $last_login_date == false) { // TODO: To be cleaned
1300
                $last_login_date = $last_login_date_tmp;
1301
            } else if($last_login_date_tmp != false && $last_login_date != false) { // TODO: Repeated previous condition. To be cleaned.
1302
                // Find the max and assign it to first_login_date
1303
                if(strtotime($last_login_date_tmp) > strtotime($last_login_date)) {
1304
                    $last_login_date = $last_login_date_tmp;
1305
                }
1306
            }
1307
1308
            $exercise_results_tmp = MySpace::exercises_results($row->user_id, $course_code);
1309
            $total_score_obtained += $exercise_results_tmp['score_obtained'];
1310
            $total_score_possible += $exercise_results_tmp['score_possible'];
1311
            $total_questions_answered += $exercise_results_tmp['questions_answered'];
1312
        }
1313 View Code Duplication
        if($nb_progress_lp > 0) {
1314
            $avg_progress = round($progress / $nb_progress_lp, 2);
1315
        } else {
1316
            $avg_progress = 0;
1317
        }
1318 View Code Duplication
        if($nb_score_lp > 0) {
1319
            $avg_score = round($score / $nb_score_lp, 2);
1320
        } else {
1321
            $avg_score = '-';
1322
        }
1323
        if($last_login_date) {
1324
            $last_login_date = api_convert_and_format_date($last_login_date, DATE_FORMAT_SHORT, date_default_timezone_get());
1325
        } else {
1326
            $last_login_date = '-';
1327
        }
1328 View Code Duplication
        if($total_score_possible > 0) {
1329
            $total_score_percentage = round($total_score_obtained / $total_score_possible * 100, 2);
1330
        } else {
1331
            $total_score_percentage = 0;
1332
        }
1333 View Code Duplication
        if($total_score_percentage > 0) {
1334
            $total_score = $total_score_obtained.'/'.$total_score_possible.' ('.$total_score_percentage.' %)';
1335
        } else {
1336
            $total_score = '-';
1337
        }
1338
        $return .= '<tr>';
1339
        // time spent in the course
1340
        $return .= '    <td style="width:164px;">'.api_time_to_hms($time_spent).'</td>';
1341
        // student progress in course
1342
        $return .= '    <td>'.$avg_progress.'</td>';
1343
        // student score
1344
        $return .= '    <td>'.$avg_score.'</td>';
1345
        // student messages
1346
        $return .= '    <td>'.$nb_messages.'</td>';
1347
        // student assignments
1348
        $return .= '    <td>'.$nb_assignments.'</td>';
1349
        // student exercises results (obtained score, maximum score, number of exercises answered, score percentage)
1350
        $return .= '<td width="105px;">'.$total_score.'</td>';
1351
        $return .= '<td>'.$total_questions_answered.'</td>';
1352
        // last connection
1353
        $return .= '    <td>'.$last_login_date.'</td>';
1354
        $return .= '</tr>';
1355
        $return .= '</table>';
1356
        return $return;
1357
    }
1358
1359
    /**
1360
     * This function exports the table that we see in display_tracking_course_overview()
1361
     *
1362
     */
1363
    public static function export_tracking_course_overview()
1364
    {
1365
        // database table definition
1366
        $tbl_course_rel_user = Database :: get_main_table(TABLE_MAIN_COURSE_USER);
1367
        $tbl_user = Database :: get_main_table(TABLE_MAIN_USER);
1368
1369
        // the values of the sortable table
1370
        if ($_GET['tracking_course_overview_page_nr']) {
1371
            $from = $_GET['tracking_course_overview_page_nr'];
1372
        } else {
1373
            $from = 0;
1374
        }
1375
        if ($_GET['tracking_course_overview_column']) {
1376
            $orderby = $_GET['tracking_course_overview_column'];
1377
        } else {
1378
            $orderby = 0;
1379
        }
1380
1381
        if ($_GET['tracking_course_overview_direction']) {
1382
            $direction = $_GET['tracking_course_overview_direction'];
1383
        } else {
1384
            $direction = 'ASC';
1385
        }
1386
1387
        $course_data = MySpace::get_course_data_tracking_overview($from, 1000, $orderby, $direction);
1388
1389
        $csv_content = array();
1390
1391
        // the first line of the csv file with the column headers
1392
        $csv_row = array();
1393
        $csv_row[] = get_lang('Course', '');
1394
        $csv_row[] = get_lang('AvgTimeSpentInTheCourse', '');
1395
        $csv_row[] = get_lang('AvgStudentsProgress', '');
1396
        $csv_row[] = get_lang('AvgCourseScore', '');
1397
        $csv_row[] = get_lang('TotalNumberOfMessages', '');
1398
        $csv_row[] = get_lang('TotalNumberOfAssignments', '');
1399
        $csv_row[] = get_lang('TotalExercisesScoreObtained', '');
1400
        $csv_row[] = get_lang('TotalExercisesScorePossible', '');
1401
        $csv_row[] = get_lang('TotalExercisesAnswered', '');
1402
        $csv_row[] = get_lang('TotalExercisesScorePercentage', '');
1403
        $csv_row[] = get_lang('LatestLogin', '');
1404
        $csv_content[] = $csv_row;
1405
1406
        // the other lines (the data)
1407
        foreach ($course_data as $key => $course) {
1408
            $course_code = $course[0];
1409
            $courseInfo = api_get_course_info($course_code);
1410
            $course_title = $courseInfo['title'];
1411
            $courseId = $courseInfo['real_id'];
1412
1413
            $csv_row = array();
1414
            $csv_row[] = $course_title;
1415
1416
            // getting all the courses of the session
1417
            $sql = "SELECT *
1418
                    FROM $tbl_user AS u
1419
                    INNER JOIN $tbl_course_rel_user AS cu
1420
                    ON cu.user_id = u.user_id
1421
                    WHERE cu.c_id = '".$courseId."'";
1422
            $result = Database::query($sql);
1423
            $time_spent = 0;
1424
            $progress = 0;
1425
            $nb_progress_lp = 0;
1426
            $score = 0;
1427
            $nb_score_lp = 0;
1428
            $nb_messages = 0;
1429
            $nb_assignments = 0;
1430
            $last_login_date = false;
1431
            $total_score_obtained = 0;
1432
            $total_score_possible = 0;
1433
            $total_questions_answered = 0;
1434 View Code Duplication
            while ($row = Database::fetch_object($result)) {
1435
                // get time spent in the course and session
1436
                $time_spent += Tracking::get_time_spent_on_the_course($row->user_id, $courseId);
1437
                $progress_tmp = Tracking::get_avg_student_progress($row->user_id, $course_code, array(), null, true);
1438
                $progress += $progress_tmp[0];
1439
                $nb_progress_lp += $progress_tmp[1];
1440
                $score_tmp = Tracking :: get_avg_student_score($row->user_id, $course_code, array(), null, true);
1441
                if(is_array($score_tmp)) {
1442
                    $score += $score_tmp[0];
1443
                    $nb_score_lp += $score_tmp[1];
1444
                }
1445
                $nb_messages += Tracking::count_student_messages($row->user_id, $course_code);
1446
                $nb_assignments += Tracking::count_student_assignments($row->user_id, $course_code);
1447
1448
                $last_login_date_tmp = Tracking::get_last_connection_date_on_the_course($row->user_id, $courseInfo, null, false);
1449
                if($last_login_date_tmp != false && $last_login_date == false) { // TODO: To be cleaned.
1450
                    $last_login_date = $last_login_date_tmp;
1451
                } else if($last_login_date_tmp != false && $last_login_date == false) { // TODO: Repeated previous condition. To be cleaned.
1452
                    // Find the max and assign it to first_login_date
1453
                    if(strtotime($last_login_date_tmp) > strtotime($last_login_date)) {
1454
                        $last_login_date = $last_login_date_tmp;
1455
                    }
1456
                }
1457
1458
                $exercise_results_tmp = MySpace::exercises_results($row->user_id, $course_code);
1459
                $total_score_obtained += $exercise_results_tmp['score_obtained'];
1460
                $total_score_possible += $exercise_results_tmp['score_possible'];
1461
                $total_questions_answered += $exercise_results_tmp['questions_answered'];
1462
            }
1463 View Code Duplication
            if($nb_progress_lp > 0) {
1464
                $avg_progress = round($progress / $nb_progress_lp, 2);
1465
            } else {
1466
                $avg_progress = 0;
1467
            }
1468 View Code Duplication
            if($nb_score_lp > 0) {
1469
                $avg_score = round($score / $nb_score_lp, 2);
1470
            } else {
1471
                $avg_score = '-';
1472
            }
1473
            if($last_login_date) {
1474
                $last_login_date = api_convert_and_format_date($last_login_date, DATE_FORMAT_SHORT, date_default_timezone_get());
1475
            } else {
1476
                $last_login_date = '-';
1477
            }
1478 View Code Duplication
            if($total_score_possible > 0) {
1479
                $total_score_percentage = round($total_score_obtained / $total_score_possible * 100, 2);
1480
            } else {
1481
                $total_score_percentage = 0;
1482
            }
1483
            // time spent in the course
1484
            $csv_row[] = api_time_to_hms($time_spent);
1485
            // student progress in course
1486
            $csv_row[] = $avg_progress;
1487
            // student score
1488
            $csv_row[] = $avg_score;
1489
            // student messages
1490
            $csv_row[] = $nb_messages;
1491
            // student assignments
1492
            $csv_row[] = $nb_assignments;
1493
            // student exercises results (obtained score, maximum score, number of exercises answered, score percentage)
1494
            $csv_row[] = $total_score_obtained;
1495
            $csv_row[] = $total_score_possible;
1496
            $csv_row[] = $total_questions_answered;
1497
            $csv_row[] = $total_score_percentage;
1498
            // last connection
1499
            $csv_row[] = $last_login_date;
1500
            $csv_content[] = $csv_row;
1501
        }
1502
        Export :: arrayToCsv($csv_content, 'reporting_course_overview');
1503
        exit;
1504
    }
1505
1506
    /**
1507
     * Display a sortable table that contains an overview of all the reporting progress of all sessions and all courses the user is subscribed to
1508
     * @author Guillaume Viguier <[email protected]>
1509
     */
1510
    public static function display_tracking_session_overview()
1511
    {
1512
        $t_head = '    <table style="width: 100%;border:0;padding:0;border-collapse:collapse;table-layout: fixed">';
1513
        //$t_head .= '  <caption>'.get_lang('CourseInformation').'</caption>';
1514
        $t_head .=      '<tr>';
1515
        $t_head .= '        <th width="155px" style="border-left:0;border-bottom:0"><span>'.get_lang('Course').'</span></th>';
1516
        $t_head .= '        <th style="padding:0;border-bottom:0"><span>'.cut(get_lang('AvgTimeSpentInTheCourse'), 6, true).'</span></th>';
1517
        $t_head .= '        <th style="padding:0;border-bottom:0"><span>'.cut(get_lang('AvgStudentsProgress'), 6, true).'</span></th>';
1518
        $t_head .= '        <th style="padding:0;border-bottom:0"><span>'.cut(get_lang('AvgCourseScore'), 6, true).'</span></th>';
1519
        //$t_head .= '      <th><div style="width:40px">'.get_lang('AvgExercisesScore').'</div></th>';
1520
        $t_head .= '        <th style="padding:0;border-bottom:0"><span>'.cut(get_lang('TotalNumberOfMessages'), 6, true).'</span></th>';
1521
        $t_head .= '        <th style="padding:0;border-bottom:0"><span>'.cut(get_lang('TotalNumberOfAssignments'), 6, true).'</span></th>';
1522
        $t_head .= '        <th width="105px" style="border-bottom:0"><span>'.get_lang('TotalExercisesScoreObtained').'</span></th>';
1523
        //$t_head .= '      <th><div>'.get_lang('TotalExercisesScorePossible').'</div></th>';
1524
        $t_head .= '        <th style="padding:0;border-bottom:0"><span>'.cut(get_lang('TotalExercisesAnswered'), 6, true).'</span></th>';
1525
        //$t_head .= '      <th><div>'.get_lang('TotalExercisesScorePercentage').'</div></th>';
1526
        //$t_head .= '      <th><div style="width:60px">'.get_lang('FirstLogin').'</div></th>';
1527
        $t_head .= '        <th style="padding:0;border-bottom:0;border-right:0;"><span>'.get_lang('LatestLogin').'</span></th>';
1528
        $t_head .= '    </tr></table>';
1529
1530
        $addparams = array('view' => 'admin', 'display' => 'sessionoverview');
1531
1532
        $table = new SortableTable('tracking_session_overview', array('MySpace','get_total_number_sessions'), array('MySpace','get_session_data_tracking_overview'), 1);
1533
        $table->additional_parameters = $addparams;
1534
1535
        $table->set_header(0, '', false, null, array('style' => 'display: none'));
1536
        $table->set_header(1, get_lang('Session'), true, array('style' => 'font-size:8pt'), array('style' => 'font-size:8pt'));
1537
        $table->set_header(2, $t_head, false, array('style' => 'width:90%;border:0;padding:0;font-size:7.5pt;'), array('style' => 'width:90%;padding:0;font-size:7.5pt;'));
1538
        $table->set_column_filter(2, array('MySpace', 'session_tracking_filter'));
1539
        $table->display();
1540
    }
1541
1542
    /**
1543
     * Get the total number of sessions
1544
     *
1545
     * @return integer Total number of sessions
1546
     */
1547
    public static function get_total_number_sessions()
1548
    {
1549
        // database table definition
1550
        $main_session_table = Database :: get_main_table(TABLE_MAIN_SESSION);
1551
        return Database::count_rows($main_session_table);
0 ignored issues
show
Deprecated Code introduced by
The method Database::count_rows() has been deprecated.

This method has been deprecated.

Loading history...
1552
    }
1553
1554
    /**
1555
     * Get data for the sessions
1556
     *
1557
     * @param int Inferior limit
1558
     * @param int Number of items to select
1559
     * @param string Column to order on
1560
     * @param string Order direction
1561
     * @return array Results
1562
     */
1563
    public static function get_session_data_tracking_overview($from, $number_of_items, $column, $direction)
1564
    {
1565
        $main_session_table = Database :: get_main_table(TABLE_MAIN_SESSION);
1566
1567
        $sql = "SELECT id AS col0, name AS col1 FROM $main_session_table";
1568
        $sql .= " ORDER BY col$column $direction ";
1569
        $sql .= " LIMIT $from,$number_of_items";
1570
        $result = Database::query($sql);
1571
        $return = array ();
1572
        while ($session = Database::fetch_row($result)) {
1573
            $return[] = $session;
1574
        }
1575
        return $return;
1576
    }
1577
1578
    /**
1579
     * Fills in session reporting data
1580
     *
1581
     * @param integer $user_id the id of the user
0 ignored issues
show
Bug introduced by
There is no parameter named $user_id. Was it maybe removed?

This check looks for PHPDoc comments describing methods or function parameters that do not exist on the corresponding method or function.

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

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

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

Loading history...
1582
     * @param array $url_params additonal url parameters
1583
     * @param array $row the row information (the other columns)
1584
     * @return string html code
1585
     */
1586
    public static function session_tracking_filter($session_id, $url_params, $row)
1587
    {
1588
        $session_id = $row[0];
1589
        // the table header
1590
        $return = '<table class="data_table" style="width: 100%;border:0;padding:0;border-collapse:collapse;table-layout: fixed">';
1591
        /*$return .= '  <tr>';
1592
        $return .= '        <th>'.get_lang('Course').'</th>';
1593
        $return .= '        <th>'.get_lang('AvgTimeSpentInTheCourse').'</th>';
1594
        $return .= '        <th>'.get_lang('AvgStudentsProgress').'</th>';
1595
        $return .= '        <th>'.get_lang('AvgCourseScore').'</th>';
1596
        $return .= '        <th>'.get_lang('AvgExercisesScore').'</th>';
1597
        $return .= '        <th>'.get_lang('AvgMessages').'</th>';
1598
        $return .= '        <th>'.get_lang('AvgAssignments').'</th>';
1599
        $return .= '        <th>'.get_lang('TotalExercisesScoreObtained').'</th>';
1600
        $return .= '        <th>'.get_lang('TotalExercisesScorePossible').'</th>';
1601
        $return .= '        <th>'.get_lang('TotalExercisesAnswered').'</th>';
1602
        $return .= '        <th>'.get_lang('TotalExercisesScorePercentage').'</th>';
1603
        $return .= '        <th>'.get_lang('FirstLogin').'</th>';
1604
        $return .= '        <th>'.get_lang('LatestLogin').'</th>';
1605
        $return .= '    </tr>';*/
1606
1607
        // database table definition
1608
        $tbl_session_rel_course = Database :: get_main_table(TABLE_MAIN_SESSION_COURSE);
1609
        $tbl_course = Database :: get_main_table(TABLE_MAIN_COURSE);
1610
        $tbl_session_rel_course_rel_user = Database :: get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
1611
        $tbl_user = Database :: get_main_table(TABLE_MAIN_USER);
1612
1613
        // getting all the courses of the user
1614
        $sql = "SELECT * FROM $tbl_course AS c
1615
                INNER JOIN $tbl_session_rel_course AS sc
1616
                ON sc.c_id = c.id
1617
                WHERE sc.session_id = '".$session_id."';";
1618
        $result = Database::query($sql);
1619
        while ($row = Database::fetch_object($result)) {
1620
            $courseId = $row->c_id;
1621
            $courseInfo = api_get_course_info_by_id($courseId);
1622
            $return .= '<tr>';
1623
            // course code
1624
            $return .= '    <td width="157px" >'.$row->title.'</td>';
1625
            // get the users in the course
1626
            $sql = "SELECT u.user_id
1627
                    FROM $tbl_user AS u
1628
                    INNER JOIN $tbl_session_rel_course_rel_user AS scu
1629
                    ON u.user_id = scu.user_id
1630
                    WHERE scu.session_id = '".$session_id."' AND scu.c_id = '".$courseId."'";
1631
            $result_users = Database::query($sql);
1632
            $time_spent = 0;
1633
            $progress = 0;
1634
            $nb_progress_lp = 0;
1635
            $score = 0;
1636
            $nb_score_lp = 0;
1637
            $nb_messages = 0;
1638
            $nb_assignments = 0;
1639
            $last_login_date = false;
1640
            $total_score_obtained = 0;
1641
            $total_score_possible = 0;
1642
            $total_questions_answered = 0;
1643 View Code Duplication
            while ($row_user = Database::fetch_object($result_users)) {
1644
                // get time spent in the course and session
1645
                $time_spent += Tracking::get_time_spent_on_the_course($row_user->user_id, $courseId, $session_id);
1646
                $progress_tmp = Tracking::get_avg_student_progress($row_user->user_id, $row->code, array(), $session_id, true);
1647
                $progress += $progress_tmp[0];
1648
                $nb_progress_lp += $progress_tmp[1];
1649
                $score_tmp = Tracking :: get_avg_student_score($row_user->user_id, $row->code, array(), $session_id, true);
1650
                if (is_array($score_tmp)) {
1651
                    $score += $score_tmp[0];
1652
                    $nb_score_lp += $score_tmp[1];
1653
                }
1654
                $nb_messages += Tracking::count_student_messages($row_user->user_id, $row->code, $session_id);
1655
                $nb_assignments += Tracking::count_student_assignments($row_user->user_id, $row->code, $session_id);
1656
                $last_login_date_tmp = Tracking::get_last_connection_date_on_the_course($row_user->user_id, $courseInfo, $session_id, false);
1657
                if ($last_login_date_tmp != false && $last_login_date == false) {
1658
                    // TODO: To be cleaned.
1659
                    $last_login_date = $last_login_date_tmp;
1660
                } else if($last_login_date_tmp != false && $last_login_date != false) {
1661
                    // TODO: Repeated previous condition! To be cleaned.
1662
                    // Find the max and assign it to first_login_date
1663
                    if(strtotime($last_login_date_tmp) > strtotime($last_login_date)) {
1664
                        $last_login_date = $last_login_date_tmp;
1665
                    }
1666
                }
1667
1668
                $exercise_results_tmp = MySpace::exercises_results($row_user->user_id, $row->code, $session_id);
1669
                $total_score_obtained += $exercise_results_tmp['score_obtained'];
1670
                $total_score_possible += $exercise_results_tmp['score_possible'];
1671
                $total_questions_answered += $exercise_results_tmp['questions_answered'];
1672
            }
1673 View Code Duplication
            if($nb_progress_lp > 0) {
1674
                $avg_progress = round($progress / $nb_progress_lp, 2);
1675
            } else {
1676
                $avg_progress = 0;
1677
            }
1678 View Code Duplication
            if($nb_score_lp > 0) {
1679
                $avg_score = round($score / $nb_score_lp, 2);
1680
            } else {
1681
                $avg_score = '-';
1682
            }
1683
            if($last_login_date) {
1684
                $last_login_date = api_convert_and_format_date($last_login_date, DATE_FORMAT_SHORT, date_default_timezone_get());
1685
            } else {
1686
                $last_login_date = '-';
1687
            }
1688 View Code Duplication
            if($total_score_possible > 0) {
1689
                $total_score_percentage = round($total_score_obtained / $total_score_possible * 100, 2);
1690
            } else {
1691
                $total_score_percentage = 0;
1692
            }
1693 View Code Duplication
            if($total_score_percentage > 0) {
1694
                $total_score = $total_score_obtained.'/'.$total_score_possible.' ('.$total_score_percentage.' %)';
1695
            } else {
1696
                $total_score = '-';
1697
            }
1698
            // time spent in the course
1699
            $return .= '    <td><div>'.api_time_to_hms($time_spent).'</div></td>';
1700
            // student progress in course
1701
            $return .= '    <td><div>'.$avg_progress.'</div></td>';
1702
            // student score
1703
            $return .= '    <td><div>'.$avg_score.'</div></td>';
1704
            // student messages
1705
            $return .= '    <td><div>'.$nb_messages.'</div></td>';
1706
            // student assignments
1707
            $return .= '    <td><div>'.$nb_assignments.'</div></td>';
1708
            // student exercises results (obtained score, maximum score, number of exercises answered, score percentage)
1709
            $return .= '<td width="105px;">'.$total_score.'</td>';
1710
            $return .= '<td>'.$total_questions_answered.'</td>';
1711
            // last connection
1712
            $return .= '    <td><div>'.$last_login_date.'</div></td>';
1713
            $return .= '<tr>';
1714
        }
1715
        $return .= '</table>';
1716
        return $return;
1717
    }
1718
1719
    /**
1720
     * This function exports the table that we see in display_tracking_session_overview()
1721
     *
1722
     */
1723
    public static function export_tracking_session_overview()
1724
    {
1725
        // database table definition
1726
        $tbl_session_rel_course = Database :: get_main_table(TABLE_MAIN_SESSION_COURSE);
1727
        $tbl_course = Database :: get_main_table(TABLE_MAIN_COURSE);
1728
        $tbl_session_rel_course_rel_user = Database :: get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
1729
        $tbl_user = Database :: get_main_table(TABLE_MAIN_USER);
1730
1731
        // the values of the sortable table
1732
        if ($_GET['tracking_session_overview_page_nr']) {
1733
            $from = $_GET['tracking_session_overview_page_nr'];
1734
        } else {
1735
            $from = 0;
1736
        }
1737
        if ($_GET['tracking_session_overview_column']) {
1738
            $orderby = $_GET['tracking_session_overview_column'];
1739
        } else {
1740
            $orderby = 0;
1741
        }
1742
1743
        if ($_GET['tracking_session_overview_direction']) {
1744
            $direction = $_GET['tracking_session_overview_direction'];
1745
        } else {
1746
            $direction = 'ASC';
1747
        }
1748
1749
        $session_data = MySpace::get_session_data_tracking_overview($from, 1000, $orderby, $direction);
1750
1751
        $csv_content = array();
1752
1753
        // the first line of the csv file with the column headers
1754
        $csv_row = array();
1755
        $csv_row[] = get_lang('Session');
1756
        $csv_row[] = get_lang('Course', '');
1757
        $csv_row[] = get_lang('AvgTimeSpentInTheCourse', '');
1758
        $csv_row[] = get_lang('AvgStudentsProgress', '');
1759
        $csv_row[] = get_lang('AvgCourseScore', '');
1760
        $csv_row[] = get_lang('TotalNumberOfMessages', '');
1761
        $csv_row[] = get_lang('TotalNumberOfAssignments', '');
1762
        $csv_row[] = get_lang('TotalExercisesScoreObtained', '');
1763
        $csv_row[] = get_lang('TotalExercisesScorePossible', '');
1764
        $csv_row[] = get_lang('TotalExercisesAnswered', '');
1765
        $csv_row[] = get_lang('TotalExercisesScorePercentage', '');
1766
        $csv_row[] = get_lang('LatestLogin', '');
1767
        $csv_content[] = $csv_row;
1768
1769
        // the other lines (the data)
1770
        foreach ($session_data as $key => $session) {
1771
            $session_id = $session[0];
1772
            $session_title = $session[1];
1773
1774
            // getting all the courses of the session
1775
            $sql = "SELECT * FROM $tbl_course AS c
1776
                    INNER JOIN $tbl_session_rel_course AS sc
1777
                    ON sc.c_id = c.id
1778
                    WHERE sc.session_id = '".$session_id."';";
1779
            $result = Database::query($sql);
1780
            while ($row = Database::fetch_object($result)) {
1781
                $courseId = $row->c_id;
1782
                $courseInfo = api_get_course_info_by_id($courseId);
1783
                $csv_row = array();
1784
                $csv_row[] = $session_title;
1785
                $csv_row[] = $row->title;
1786
                // get the users in the course
1787
                $sql = "SELECT scu.user_id
1788
                        FROM $tbl_user AS u
1789
                        INNER JOIN $tbl_session_rel_course_rel_user AS scu
1790
                        ON u.user_id = scu.user_id
1791
                        WHERE scu.session_id = '".$session_id."' AND scu.c_id = '".$courseId."'";
1792
                $result_users = Database::query($sql);
1793
                $time_spent = 0;
1794
                $progress = 0;
1795
                $nb_progress_lp = 0;
1796
                $score = 0;
1797
                $nb_score_lp = 0;
1798
                $nb_messages = 0;
1799
                $nb_assignments = 0;
1800
                $last_login_date = false;
1801
                $total_score_obtained = 0;
1802
                $total_score_possible = 0;
1803
                $total_questions_answered = 0;
1804 View Code Duplication
                while($row_user = Database::fetch_object($result_users)) {
1805
                    // get time spent in the course and session
1806
                    $time_spent += Tracking::get_time_spent_on_the_course($row_user->user_id, $courseId, $session_id);
1807
                    $progress_tmp = Tracking::get_avg_student_progress($row_user->user_id, $row->code, array(), $session_id, true);
1808
                    $progress += $progress_tmp[0];
1809
                    $nb_progress_lp += $progress_tmp[1];
1810
                    $score_tmp = Tracking :: get_avg_student_score($row_user->user_id, $row->code, array(), $session_id, true);
1811
                    if (is_array($score_tmp)) {
1812
                        $score += $score_tmp[0];
1813
                        $nb_score_lp += $score_tmp[1];
1814
                    }
1815
                    $nb_messages += Tracking::count_student_messages(
1816
                        $row_user->user_id,
1817
                        $row->code,
1818
                        $session_id
1819
                    );
1820
1821
                    $nb_assignments += Tracking::count_student_assignments(
1822
                        $row_user->user_id,
1823
                        $row->code,
1824
                        $session_id
1825
                    );
1826
1827
                    $last_login_date_tmp = Tracking:: get_last_connection_date_on_the_course(
1828
                        $row_user->user_id,
1829
                        $courseInfo,
1830
                        $session_id,
1831
                        false
1832
                    );
1833
                    if($last_login_date_tmp != false && $last_login_date == false) { // TODO: To be cleaned.
1834
                        $last_login_date = $last_login_date_tmp;
1835
                    } else if($last_login_date_tmp != false && $last_login_date == false) { // TODO: Repeated previous condition. To be cleaned.
1836
                        // Find the max and assign it to first_login_date
1837
                        if(strtotime($last_login_date_tmp) > strtotime($last_login_date)) {
1838
                            $last_login_date = $last_login_date_tmp;
1839
                        }
1840
                    }
1841
1842
                    $exercise_results_tmp = MySpace::exercises_results($row_user->user_id, $row->code, $session_id);
1843
                    $total_score_obtained += $exercise_results_tmp['score_obtained'];
1844
                    $total_score_possible += $exercise_results_tmp['score_possible'];
1845
                    $total_questions_answered += $exercise_results_tmp['questions_answered'];
1846
                }
1847 View Code Duplication
                if($nb_progress_lp > 0) {
1848
                    $avg_progress = round($progress / $nb_progress_lp, 2);
1849
                } else {
1850
                    $avg_progress = 0;
1851
                }
1852 View Code Duplication
                if($nb_score_lp > 0) {
1853
                    $avg_score = round($score / $nb_score_lp, 2);
1854
                } else {
1855
                    $avg_score = '-';
1856
                }
1857
                if($last_login_date) {
1858
                    $last_login_date = api_convert_and_format_date($last_login_date, DATE_FORMAT_SHORT, date_default_timezone_get());
1859
                } else {
1860
                    $last_login_date = '-';
1861
                }
1862 View Code Duplication
                if($total_score_possible > 0) {
1863
                    $total_score_percentage = round($total_score_obtained / $total_score_possible * 100, 2);
1864
                } else {
1865
                    $total_score_percentage = 0;
1866
                }
1867 View Code Duplication
                if($total_score_percentage > 0) {
1868
                    $total_score = $total_score_obtained.'/'.$total_score_possible.' ('.$total_score_percentage.' %)';
1869
                } else {
1870
                    $total_score = '-';
1871
                }
1872
                // time spent in the course
1873
                $csv_row[] = api_time_to_hms($time_spent);
1874
                // student progress in course
1875
                $csv_row[] = $avg_progress;
1876
                // student score
1877
                $csv_row[] = $avg_score;
1878
                // student messages
1879
                $csv_row[] = $nb_messages;
1880
                // student assignments
1881
                $csv_row[] = $nb_assignments;
1882
                // student exercises results (obtained score, maximum score, number of exercises answered, score percentage)
1883
                $csv_row[] = $total_score_obtained;
1884
                $csv_row[] = $total_score_possible;
1885
                $csv_row[] = $total_questions_answered;
1886
                $csv_row[] = $total_score_percentage;
1887
                // last connection
1888
                $csv_row[] = $last_login_date;
1889
                $csv_content[] = $csv_row;
1890
            }
1891
        }
1892
        Export :: arrayToCsv($csv_content, 'reporting_session_overview');
1893
        exit;
1894
    }
1895
1896
    /**
1897
     * Get general information about the exercise performance of the user
1898
     * the total obtained score (all the score on all the questions)
1899
     * the maximum score that could be obtained
1900
     * the number of questions answered
1901
     * the success percentage
1902
     * @param integer $user_id the id of the user
1903
     * @param string $course_code the course code
1904
     * @return array
1905
     * @author Patrick Cool <[email protected]>, Ghent University, Belgium
1906
     * @version Dokeos 1.8.6
1907
     * @since November 2008
1908
     */
1909
    public static function exercises_results($user_id, $course_code, $session_id = false)
1910
    {
1911
        $questions_answered = 0;
1912
        $courseId = api_get_course_int_id($course_code);
1913
        $sql = 'SELECT exe_result , exe_weighting
1914
            FROM '.Database :: get_main_table(TABLE_STATISTIC_TRACK_E_EXERCISES)."
1915
            WHERE c_id = ' . $courseId . '
1916
            AND exe_user_id = '".intval($user_id)."'";
1917
        if($session_id !== false) {
1918
            $sql .= " AND session_id = '".$session_id."' ";
1919
        }
1920
        $result = Database::query($sql);
1921
        $score_obtained = 0;
1922
        $score_possible = 0;
1923
        $questions_answered = 0;
1924
        while ($row = Database::fetch_array($result)) {
1925
            $score_obtained += $row['exe_result'];
1926
            $score_possible += $row['exe_weighting'];
1927
            $questions_answered ++;
1928
        }
1929
1930
        if ($score_possible != 0) {
1931
            $percentage = round(($score_obtained / $score_possible * 100), 2);
1932
        } else {
1933
            $percentage = null;
1934
        }
1935
1936
        return array(
1937
            'score_obtained' => $score_obtained,
1938
            'score_possible' => $score_possible,
1939
            'questions_answered' => $questions_answered,
1940
            'percentage' => $percentage
1941
        );
1942
    }
1943
1944
    /**
1945
     * This function exports the table that we see in display_tracking_user_overview()
1946
     *
1947
     * @author Patrick Cool <[email protected]>, Ghent University, Belgium
1948
     * @version Dokeos 1.8.6
1949
     * @since October 2008
1950
     */
1951
    public static function export_tracking_user_overview()
1952
    {
1953
        // database table definitions
1954
        $tbl_course_user = Database :: get_main_table(TABLE_MAIN_COURSE_USER);
1955
1956
        $is_western_name_order = api_is_western_name_order(PERSON_NAME_DATA_EXPORT);
1957
        $sort_by_first_name = api_sort_by_first_name();
1958
1959
        // the values of the sortable table
1960
        if ($_GET['tracking_user_overview_page_nr']) {
1961
            $from = $_GET['tracking_user_overview_page_nr'];
1962
        } else {
1963
            $from = 0;
1964
        }
1965
        if ($_GET['tracking_user_overview_column']) {
1966
            $orderby = $_GET['tracking_user_overview_column'];
1967
        } else {
1968
            $orderby = 0;
1969
        }
1970
        if ($is_western_name_order != api_is_western_name_order() && ($orderby == 1 || $orderby == 2)) {
1971
            // Swapping the sorting column if name order for export is different than the common name order.
1972
            $orderby = 3 - $orderby;
1973
        }
1974
        if ($_GET['tracking_user_overview_direction']) {
1975
            $direction = $_GET['tracking_user_overview_direction'];
1976
        } else {
1977
            $direction = 'ASC';
1978
        }
1979
1980
        $user_data = MySpace::get_user_data_tracking_overview($from, 1000, $orderby, $direction);
1981
1982
        // the first line of the csv file with the column headers
1983
        $csv_row = array();
1984
        $csv_row[] = get_lang('OfficialCode');
1985 View Code Duplication
        if ($is_western_name_order) {
1986
            $csv_row[] = get_lang('FirstName', '');
1987
            $csv_row[] = get_lang('LastName', '');
1988
        } else {
1989
            $csv_row[] = get_lang('LastName', '');
1990
            $csv_row[] = get_lang('FirstName', '');
1991
        }
1992
        $csv_row[] = get_lang('LoginName');
1993
        $csv_row[] = get_lang('CourseCode');
1994
        // the additional user defined fields (only those that were selected to be exported)
1995
1996
        $fields = UserManager::get_extra_fields(0, 50, 5, 'ASC');
1997
1998
        if (is_array($_SESSION['additional_export_fields'])) {
1999
            foreach ($_SESSION['additional_export_fields'] as $key => $extra_field_export) {
2000
                $csv_row[] = $fields[$extra_field_export][3];
2001
                $field_names_to_be_exported[] = 'extra_'.$fields[$extra_field_export][1];
2002
            }
2003
        }
2004
        $csv_row[] = get_lang('AvgTimeSpentInTheCourse', '');
2005
        $csv_row[] = get_lang('AvgStudentsProgress', '');
2006
        $csv_row[] = get_lang('AvgCourseScore', '');
2007
        $csv_row[] = get_lang('AvgExercisesScore', '');
2008
        $csv_row[] = get_lang('AvgMessages', '');
2009
        $csv_row[] = get_lang('AvgAssignments', '');
2010
        $csv_row[] = get_lang('TotalExercisesScoreObtained', '');
2011
        $csv_row[] = get_lang('TotalExercisesScorePossible', '');
2012
        $csv_row[] = get_lang('TotalExercisesAnswered', '');
2013
        $csv_row[] = get_lang('TotalExercisesScorePercentage', '');
2014
        $csv_row[] = get_lang('FirstLogin', '');
2015
        $csv_row[] = get_lang('LatestLogin', '');
2016
        $csv_content[] = $csv_row;
2017
2018
        // the other lines (the data)
2019
        foreach ($user_data as $key => $user) {
2020
            // getting all the courses of the user
2021
            $sql = "SELECT * FROM $tbl_course_user
2022
                    WHERE user_id = '".intval($user[4])."' AND relation_type<>".COURSE_RELATION_TYPE_RRHH." ";
2023
            $result = Database::query($sql);
2024
            while ($row = Database::fetch_row($result)) {
2025
                $courseInfo = api_get_course_info($row['course_code']);
2026
                $courseId = $courseInfo['real_id'];
2027
2028
                $csv_row = array();
2029
                // user official code
2030
                $csv_row[] = $user[0];
2031
                // user first|last name
2032
                $csv_row[] = $user[1];
2033
                // user last|first name
2034
                $csv_row[] = $user[2];
2035
                // user login name
2036
                $csv_row[] = $user[3];
2037
                // course code
2038
                $csv_row[] = $row[0];
2039
                // the additional defined user fields
2040
                $extra_fields = MySpace::get_user_overview_export_extra_fields($user[4]);
2041
2042
                if (is_array($field_names_to_be_exported)) {
2043
                    foreach ($field_names_to_be_exported as $key => $extra_field_export) {
2044
                        $csv_row[] = $extra_fields[$extra_field_export];
2045
                    }
2046
                }
2047
                // time spent in the course
2048
                $csv_row[] = api_time_to_hms(Tracking::get_time_spent_on_the_course ($user[4], $courseId));
2049
                // student progress in course
2050
                $csv_row[] = round(Tracking::get_avg_student_progress ($user[4], $row[0]), 2);
2051
                // student score
2052
                $csv_row[] = round(Tracking::get_avg_student_score($user[4], $row[0]), 2);
2053
                // student tes score
2054
                $csv_row[] = round(Tracking::get_avg_student_exercise_score($user[4], $row[0]), 2);
2055
                // student messages
2056
                $csv_row[] = Tracking::count_student_messages($user[4], $row[0]);
2057
                // student assignments
2058
                $csv_row[] = Tracking::count_student_assignments ($user[4], $row[0]);
2059
                // student exercises results
2060
                $exercises_results = MySpace::exercises_results($user[4], $row[0]);
2061
                $csv_row[] = $exercises_results['score_obtained'];
2062
                $csv_row[] = $exercises_results['score_possible'];
2063
                $csv_row[] = $exercises_results['questions_answered'];
2064
                $csv_row[] = $exercises_results['percentage'];
2065
                // first connection
2066
                $csv_row[] = Tracking::get_first_connection_date_on_the_course ($user[4], $courseId);
2067
                // last connection
2068
                $csv_row[] = strip_tags(Tracking::get_last_connection_date_on_the_course($user[4], $courseInfo));
2069
2070
                $csv_content[] = $csv_row;
2071
            }
2072
        }
2073
        Export :: arrayToCsv($csv_content, 'reporting_user_overview');
2074
        exit;
2075
    }
2076
2077
    /**
2078
     * Get data for courses list in sortable with pagination
2079
     * @return array
2080
     */
2081
    public static function get_course_data($from, $number_of_items, $column, $direction)
2082
    {
2083
        global $courses, $csv_content, $charset, $session_id;
2084
2085
        // definition database tables
2086
        $tbl_course                 = Database :: get_main_table(TABLE_MAIN_COURSE);
2087
        $tbl_course_user            = Database :: get_main_table(TABLE_MAIN_COURSE_USER);
2088
        $tbl_session_course_user    = Database :: get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
2089
2090
        $course_data = array();
2091
        $courses_code = array_keys($courses);
2092
2093
        foreach ($courses_code as &$code) {
2094
            $code = "'$code'";
2095
        }
2096
2097
        // get all courses with limit
2098
        $sql = "SELECT course.code as col1, course.title as col2
2099
                FROM $tbl_course course
2100
                WHERE course.code IN (".implode(',',$courses_code).")";
2101
2102
        if (!in_array($direction, array('ASC','DESC'))) $direction = 'ASC';
2103
2104
        $column = intval($column);
2105
        $from = intval($from);
2106
        $number_of_items = intval($number_of_items);
2107
        $sql .= " ORDER BY col$column $direction ";
2108
        $sql .= " LIMIT $from,$number_of_items";
2109
2110
        $res = Database::query($sql);
2111
        while ($row_course = Database::fetch_row($res)) {
2112
            $course_code = $row_course[0];
2113
            $courseInfo = api_get_course_info($course_code);
2114
            $courseId = $courseInfo['real_id'];
2115
            $avg_assignments_in_course = $avg_messages_in_course = $nb_students_in_course = $avg_progress_in_course = $avg_score_in_course = $avg_time_spent_in_course = $avg_score_in_exercise = 0;
2116
2117
            // students directly subscribed to the course
2118
            if (empty($session_id)) {
2119
                $sql = "SELECT user_id
2120
                        FROM $tbl_course_user as course_rel_user
2121
                        WHERE
2122
                            course_rel_user.status='5' AND
2123
                            course_rel_user.c_id = '$courseId'";
2124
            } else {
2125
                $sql = "SELECT user_id FROM $tbl_session_course_user srcu
2126
                        WHERE
2127
                            c_id = '$courseId' AND
2128
                            session_id = '$session_id' AND
2129
                            status<>2";
2130
            }
2131
            $rs = Database::query($sql);
2132
            $users = array();
2133
            while ($row = Database::fetch_array($rs)) {
2134
                $users[] = $row['user_id'];
2135
            }
2136
2137
            if (count($users) > 0) {
2138
                $nb_students_in_course = count($users);
2139
                $avg_assignments_in_course  = Tracking::count_student_assignments($users, $course_code, $session_id);
2140
                $avg_messages_in_course     = Tracking::count_student_messages($users, $course_code, $session_id);
2141
                $avg_progress_in_course     = Tracking::get_avg_student_progress($users, $course_code, array(), $session_id);
2142
                $avg_score_in_course        = Tracking::get_avg_student_score($users, $course_code, array(), $session_id);
2143
                $avg_score_in_exercise      = Tracking::get_avg_student_exercise_score($users, $course_code, 0, $session_id);
2144
                $avg_time_spent_in_course   = Tracking::get_time_spent_on_the_course($users, $courseInfo['real_id'], $session_id);
2145
2146
                $avg_progress_in_course = round($avg_progress_in_course / $nb_students_in_course, 2);
2147
                if (is_numeric($avg_score_in_course)) {
2148
                    $avg_score_in_course = round($avg_score_in_course / $nb_students_in_course, 2);
2149
                }
2150
                $avg_time_spent_in_course = api_time_to_hms($avg_time_spent_in_course / $nb_students_in_course);
2151
2152
            } else {
2153
                $avg_time_spent_in_course = null;
2154
                $avg_progress_in_course = null;
2155
                $avg_score_in_course = null;
2156
                $avg_score_in_exercise = null;
2157
                $avg_messages_in_course = null;
2158
                $avg_assignments_in_course = null;
2159
            }
2160
            $table_row = array();
2161
            $table_row[] = $row_course[1];
2162
            $table_row[] = $nb_students_in_course;
2163
            $table_row[] = $avg_time_spent_in_course;
2164
            $table_row[] = is_null($avg_progress_in_course) ? '' : $avg_progress_in_course.'%';
2165
            $table_row[] = is_null($avg_score_in_course) ? '' : $avg_score_in_course.'%';
2166
            $table_row[] = is_null($avg_score_in_exercise) ? '' : $avg_score_in_exercise.'%';
2167
            $table_row[] = $avg_messages_in_course;
2168
            $table_row[] = $avg_assignments_in_course;
2169
2170
            //set the "from" value to know if I access the Reporting by the chamilo tab or the course link
2171
            $table_row[] = '<center><a href="../../tracking/courseLog.php?cidReq=' .$course_code.'&from=myspace&id_session='.$session_id.'">
2172
                             '.Display::return_icon('2rightarrow.png').'
2173
                             </a>
2174
                            </center>';
2175
            $csv_content[] = array(
2176
                api_html_entity_decode($row_course[1], ENT_QUOTES, $charset),
2177
                $nb_students_in_course,
2178
                $avg_time_spent_in_course,
2179
                is_null($avg_progress_in_course) ? null : $avg_progress_in_course.'%',
2180
                is_null($avg_score_in_course) ? null : is_numeric($avg_score_in_course) ? $avg_score_in_course.'%' : $avg_score_in_course ,
2181
                is_null($avg_score_in_exercise) ? null : $avg_score_in_exercise.'%',
2182
                $avg_messages_in_course,
2183
                $avg_assignments_in_course,
2184
            );
2185
            $course_data[] = $table_row;
2186
        }
2187
        return $course_data;
2188
    }
2189
2190
    /**
2191
     * get the numer of users of the platform
2192
     *
2193
     * @return integer
2194
     *
2195
     * @author Patrick Cool <[email protected]>, Ghent University, Belgium
2196
     * @version Dokeos 1.8.6
2197
     * @since October 2008
2198
     */
2199
    public static function get_number_of_users_tracking_overview()
2200
    {
2201
        // database table definition
2202
        $main_user_table = Database :: get_main_table(TABLE_MAIN_USER);
2203
        return Database::count_rows($main_user_table);
0 ignored issues
show
Deprecated Code introduced by
The method Database::count_rows() has been deprecated.

This method has been deprecated.

Loading history...
2204
    }
2205
2206
    /**
2207
     * get all the data for the sortable table of the reporting progress of all users and all the courses the user is subscribed to.
2208
     *
2209
     * @author Patrick Cool <[email protected]>, Ghent University, Belgium
2210
     * @version Dokeos 1.8.6
2211
     * @since October 2008
2212
     */
2213
    public static function get_user_data_tracking_overview($from, $number_of_items, $column, $direction)
2214
    {
2215
        // database table definition
2216
        $access_url_id = api_get_current_access_url_id();
2217
        $tbl_url_rel_user = Database::get_main_table(TABLE_MAIN_ACCESS_URL_REL_USER);
2218
        $main_user_table = Database::get_main_table(TABLE_MAIN_USER);
2219
        $condition_multi_url = null;
2220
        if (api_is_multiple_url_enabled()) {
2221
            $condition_multi_url = ", $tbl_url_rel_user as url_user
2222
            WHERE user.user_id=url_user.user_id AND access_url_id='$access_url_id'";
2223
        }
2224
2225
        global $export_csv;
2226
        if ($export_csv) {
2227
            $is_western_name_order = api_is_western_name_order(PERSON_NAME_DATA_EXPORT);
2228
        } else {
2229
            $is_western_name_order = api_is_western_name_order();
2230
        }
2231
        $sql = "SELECT
2232
                    official_code AS col0,
2233
                    ".($is_western_name_order ? "
2234
                    firstname       AS col1,
2235
                    lastname        AS col2,
2236
                    " : "
2237
                    lastname        AS col1,
2238
                    firstname       AS col2,
2239
                    ").
2240
                    "username       AS col3,
2241
                    user.user_id        AS col4
2242
                FROM
2243
                $main_user_table as user $condition_multi_url
2244
                ";
2245
        $sql .= " ORDER BY col$column $direction ";
2246
        $sql .= " LIMIT $from,$number_of_items";
2247
        $result = Database::query($sql);
2248
        $return = array ();
2249
        while ($user = Database::fetch_row($result)) {
2250
            $return[] = $user;
2251
        }
2252
        return $return;
2253
    }
2254
2255
    /**
2256
     * Get all information that the user with user_id = $user_data has
2257
     * entered in the additionally defined profile fields
2258
     * @param integer $user_id the id of the user
2259
     * @author Patrick Cool <[email protected]>, Ghent University, Belgium
2260
     * @version Dokeos 1.8.6
2261
     * @since November 2008
2262
     */
2263
    public static function get_user_overview_export_extra_fields($user_id)
2264
    {
2265
        // include the user manager
2266
2267
        $extra_data = UserManager::get_extra_user_data($user_id, true);
2268
        return $extra_data;
2269
    }
2270
    /**
2271
     * Checks if a username exist in the DB otherwise it create a "double"
2272
     * i.e. if we look into for jmontoya but the user's name already exist we create the user jmontoya2
2273
     * the return array will be array(username=>'jmontoya', sufix='2')
2274
     * @param string firstname
2275
     * @param string lastname
2276
     * @param string username
2277
     * @return array with the username, the sufix
2278
     * @author Julio Montoya Armas
2279
     */
2280
    public static function make_username($firstname, $lastname, $username, $language = null, $encoding = null)
2281
    {
2282
        // if username exist
2283
        if (!UserManager::is_username_available($username) || empty($username)) {
2284
            $i = 0;
2285
            while (1) {
2286
                if ($i == 0) {
2287
                    $sufix = '';
2288
                } else {
2289
                    $sufix = $i;
2290
                }
2291
                $desired_username = UserManager::create_username(
2292
                    $firstname,
2293
                    $lastname,
2294
                    $language,
2295
                    $encoding
2296
                );
2297
                if (UserManager::is_username_available($desired_username.$sufix)) {
2298
                    break;
2299
                } else {
2300
                    $i++;
2301
                }
2302
            }
2303
            $username_array = array('username' => $desired_username , 'sufix' => $sufix);
2304
            return $username_array;
2305
        } else {
2306
            $username_array = array('username' => $username, 'sufix' => '');
2307
            return $username_array;
2308
        }
2309
    }
2310
2311
    /**
2312
     * Checks if there are repeted users in a given array
2313
     * @param  array $usernames list of the usernames in the uploaded file
2314
     * @param  array $user_array['username'] and $user_array['sufix'] where sufix is the number part in a login i.e -> jmontoya2
0 ignored issues
show
Documentation introduced by
There is no parameter named $user_array['username']. Did you maybe mean $user_array?

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...
2315
     * @return array with the $usernames array and the $user_array array
2316
     * @author Julio Montoya Armas
2317
     */
2318
    public static function check_user_in_array($usernames, $user_array)
2319
    {
2320
        $user_list = array_keys($usernames);
2321
        $username = $user_array['username'].$user_array['sufix'];
2322
2323
        if (in_array($username, $user_list)) {
2324
            $user_array['sufix'] += $usernames[$username];
2325
            $usernames[$username]++;
2326
        } else {
2327
            $usernames[$username] = 1;
2328
        }
2329
        $result_array = array($usernames, $user_array);
2330
        return $result_array;
2331
    }
2332
2333
    /**
2334
     * Checks whether a username has been already subscribed in a session.
2335
     * @param string a given username
2336
     * @param array  the array with the course list id
2337
     * @param the session id
2338
     * @return 0 if the user is not subscribed  otherwise it returns the user_id of the given username
0 ignored issues
show
Documentation introduced by
The doc-type 0 could not be parsed: Unknown type name "0" 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...
2339
     * @author Julio Montoya
2340
     */
2341
    public static function user_available_in_session($username, $course_list, $id_session)
2342
    {
2343
        $table_user = Database::get_main_table(TABLE_MAIN_USER);
2344
        $tbl_session_rel_course_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
2345
        $id_session = intval($id_session);
2346
        $username = Database::escape_string($username);
2347
        foreach ($course_list as $courseId) {
2348
            $courseId = intval($courseId);
2349
            $sql = " SELECT u.user_id FROM $tbl_session_rel_course_rel_user rel
2350
                     INNER JOIN $table_user u
2351
                     ON (rel.user_id = u.user_id)
2352
                     WHERE
2353
                        rel.session_id='$id_session' AND
2354
                        u.status='5' AND
2355
                        u.username ='$username' AND
2356
                        rel.c_id='$courseId'";
2357
            $rs = Database::query($sql);
2358
            if (Database::num_rows($rs) > 0) {
2359
                return Database::result($rs, 0, 0);
2360
            } else {
2361
                return 0;
2362
            }
2363
        }
2364
    }
2365
2366
    /**
2367
     * This function checks whether some users in the uploaded file
2368
     * repeated and creates unique usernames if necesary.
2369
     * A case: Within the file there is an user repeted twice (Julio Montoya / Julio Montoya)
2370
     * and the username fields are empty.
2371
     * Then, this function would create unique usernames based on the first and the last name.
2372
     * Two users wiould be created - jmontoya and jmontoya2.
2373
     * Of course, if in the database there is a user with the name jmontoya,
2374
     * the newly created two users registered would be jmontoya2 and jmontoya3.
2375
     * @param $users list of users
2376
     * @author Julio Montoya Armas
2377
     */
2378
    function check_all_usernames($users, $course_list, $id_session)
2379
    {
2380
        $table_user = Database::get_main_table(TABLE_MAIN_USER);
2381
        $usernames = array();
2382
        $new_users = array();
2383
        foreach ($users as $index => $user) {
2384
            $desired_username = array();
2385
            if (empty($user['UserName'])) {
2386
                $desired_username = MySpace::make_username($user['FirstName'], $user['LastName'], '');
2387
                $pre_username = $desired_username['username'].$desired_username['sufix'];
2388
                $user['UserName'] = $pre_username;
2389
                $user['create'] = '1';
2390
            } else {
2391
                if (UserManager::is_username_available($user['UserName'])) {
2392
                    $desired_username = MySpace::make_username($user['FirstName'], $user['LastName'], $user['UserName']);
2393
                    $user['UserName'] = $desired_username['username'].$desired_username['sufix'];
2394
                    $user['create'] = '1';
2395 View Code Duplication
                } else {
2396
                    $is_session_avail = MySpace::user_available_in_session($user['UserName'], $course_list, $id_session);
2397
                    if ($is_session_avail == 0) {
2398
                        $user_name = $user['UserName'];
2399
                        $sql_select = "SELECT user_id FROM $table_user WHERE username ='$user_name' ";
2400
                        $rs = Database::query($sql_select);
2401
                        $user['create'] = Database::result($rs, 0, 0); // This should be the ID because the user exists.
2402
                    } else {
2403
                        $user['create'] = $is_session_avail;
2404
                    }
2405
                }
2406
            }
2407
            // Usernames is the current list of users in the file.
2408
            $result_array = MySpace::check_user_in_array($usernames, $desired_username);
2409
            $usernames = $result_array[0];
2410
            $desired_username = $result_array[1];
2411
            $user['UserName'] = $desired_username['username'].$desired_username['sufix'];
2412
            $new_users[] = $user;
2413
        }
2414
        return $new_users;
2415
    }
2416
2417
    /**
2418
     * This functions checks whether there are users that are already
2419
     * registered in the DB by different creator than the current coach.
2420
     * @param string a given username
2421
     * @param array  the array with the course list ids
2422
     * @param the session id
2423
     * @author Julio Montoya Armas
2424
     */
2425
    public function get_user_creator($users)
2426
    {
2427
        $errors = array();
2428
        foreach ($users as $index => $user) {
2429
            // database table definition
2430
            $table_user = Database::get_main_table(TABLE_MAIN_USER);
2431
            $username = Database::escape_string($user['UserName']);
2432
            $sql = "SELECT creator_id FROM $table_user WHERE username='$username' ";
2433
2434
            $rs = Database::query($sql);
2435
            $creator_id = Database::result($rs, 0, 0);
2436
            // check if we are the creators or not
2437
            if ($creator_id != '') {
2438
                if ($creator_id != api_get_user_id()) {
2439
                    $user['error'] = get_lang('UserAlreadyRegisteredByOtherCreator');
2440
                    $errors[] = $user;
2441
                }
2442
            }
2443
        }
2444
2445
        return $errors;
2446
    }
2447
2448
    /**
2449
     * Validates imported data.
2450
     * @param list of users
2451
     */
2452
    function validate_data($users, $id_session = null)
2453
    {
2454
        $errors = array();
2455
        $new_users = array();
2456
        foreach ($users as $index => $user) {
2457
            // 1. Check whether mandatory fields are set.
2458
            $mandatory_fields = array('LastName', 'FirstName');
2459
            if (api_get_setting('registration', 'email') == 'true') {
2460
                $mandatory_fields[] = 'Email';
2461
            }
2462
2463
            foreach ($mandatory_fields as $key => $field) {
2464
                if (!isset ($user[$field]) || strlen($user[$field]) == 0) {
2465
                    $user['error'] = get_lang($field.'Mandatory');
2466
                    $errors[] = $user;
2467
                }
2468
            }
2469
            // 2. Check whether the username is too long.
2470 View Code Duplication
            if (UserManager::is_username_too_long($user['UserName'])) {
2471
                $user['error'] = get_lang('UserNameTooLong');
2472
                $errors[] = $user;
2473
            }
2474
2475
            $user['UserName'] = trim($user['UserName']);
2476
2477
            if (empty($user['UserName'])) {
2478
                $user['UserName'] = UserManager::create_username($user['FirstName'], $user['LastName']);
2479
            }
2480
            $new_users[] = $user;
2481
        }
2482
        $results = array('errors' => $errors, 'users' => $new_users);
2483
        return $results;
2484
    }
2485
2486
    /**
2487
     * Adds missing user-information (which isn't required, like password, etc).
2488
     */
2489
    function complete_missing_data($user) {
2490
        // 1. Generate a password if it is necessary.
2491 View Code Duplication
        if (!isset ($user['Password']) || strlen($user['Password']) == 0) {
2492
            $user['Password'] = api_generate_password();
2493
        }
2494
2495
        return $user;
2496
    }
2497
2498
    /**
2499
     * Saves imported data.
2500
     */
2501
    public function save_data($users, $course_list, $id_session)
2502
    {
2503
        $tbl_session = Database::get_main_table(TABLE_MAIN_SESSION);
2504
        $tbl_session_rel_course = Database::get_main_table(TABLE_MAIN_SESSION_COURSE);
2505
        $tbl_session_rel_course_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_COURSE_USER);
2506
        $tbl_session_rel_user = Database::get_main_table(TABLE_MAIN_SESSION_USER);
2507
2508
        $id_session = intval($id_session);
2509
        $sendMail = $_POST['sendMail'] ? 1 : 0;
2510
2511
        // Adding users to the platform.
2512
        $new_users = array();
2513
        foreach ($users as $index => $user) {
2514
            $user = MySpace::complete_missing_data($user);
2515
            // coach only will registered users
2516
            $default_status = STUDENT;
2517
            if ($user['create'] == COURSEMANAGER) {
2518
                $user['id'] = UserManager:: create_user(
2519
                    $user['FirstName'],
2520
                    $user['LastName'],
2521
                    $default_status,
2522
                    $user['Email'],
2523
                    $user['UserName'],
2524
                    $user['Password'],
2525
                    $user['OfficialCode'],
2526
                    api_get_setting('PlatformLanguage'),
2527
                    $user['PhoneNumber'],
2528
                    ''
2529
                );
2530
                $user['added_at_platform'] = 1;
2531
            } else {
2532
                $user['id'] = $user['create'];
2533
                $user['added_at_platform'] = 0;
2534
            }
2535
            $new_users[] = $user;
2536
        }
2537
        // Update user list.
2538
        $users = $new_users;
2539
2540
        // Inserting users.
2541
        $super_list = array();
2542
        foreach ($course_list as $enreg_course) {
2543
            $nbr_users = 0;
2544
            $new_users = array();
2545
            $enreg_course = Database::escape_string($enreg_course);
2546
            foreach ($users as $index => $user) {
2547
                $userid = intval($user['id']);
2548
                $sql = "INSERT IGNORE INTO $tbl_session_rel_course_rel_user(session_id, c_id, user_id)
2549
                        VALUES('$id_session','$enreg_course','$userid')";
2550
                $course_session = array('course' => $enreg_course, 'added' => 1);
2551
2552
                $result = Database::query($sql);
2553
                if (Database::affected_rows($result)) {
2554
                    $nbr_users++;
2555
                }
2556
                $new_users[] = $user;
2557
            }
2558
            $super_list[] = $new_users;
2559
2560
            //update the nbr_users field
2561
            $sql_select = "SELECT COUNT(user_id) as nbUsers FROM $tbl_session_rel_course_rel_user
2562
                           WHERE session_id='$id_session' AND c_id='$enreg_course'";
2563
            $rs = Database::query($sql_select);
2564
            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...
2565
            $sql_update = "UPDATE $tbl_session_rel_course SET nbr_users=$nbr_users
2566
                           WHERE session_id='$id_session' AND c_id='$enreg_course'";
2567
            Database::query($sql_update);
2568
2569
            $sql_update = "UPDATE $tbl_session SET nbr_users= '$nbr_users' WHERE id='$id_session'";
2570
            Database::query($sql_update);
2571
        }
2572
2573
        $new_users = array();
2574
        foreach ($users as $index => $user) {
2575
            $userid = $user['id'];
2576
            $sql_insert = "INSERT IGNORE INTO $tbl_session_rel_user(session_id, user_id, registered_at)
2577
                           VALUES ('$id_session','$userid', '" . api_get_utc_datetime() . "')";
2578
            Database::query($sql_insert);
2579
            $user['added_at_session'] = 1;
2580
            $new_users[] = $user;
2581
        }
2582
2583
        $users = $new_users;
2584
        $registered_users = get_lang('FileImported').'<br /> Import file results : <br />';
2585
        // Sending emails.
2586
        $addedto = '';
2587
        if ($sendMail) {
2588
            $i = 0;
2589
            foreach ($users as $index => $user) {
2590
                $emailsubject = '['.api_get_setting('siteName').'] '.get_lang('YourReg').' '.api_get_setting('siteName');
2591
                $emailbody = get_lang('Dear').' '.
2592
                    api_get_person_name($user['FirstName'], $user['LastName']).",\n\n".
2593
                    get_lang('YouAreReg')." ".api_get_setting('siteName')." ".get_lang('WithTheFollowingSettings')."\n\n".
2594
                    get_lang('Username')." : $user[UserName]\n".
2595
                    get_lang('Pass')." : $user[Password]\n\n".
2596
                    get_lang('Address')." ".api_get_setting('siteName')." ".get_lang('Is')." : ".api_get_path(WEB_PATH)." \n\n".
2597
                    get_lang('Problem')."\n\n".
2598
                    get_lang('SignatureFormula').",\n\n".
2599
                    api_get_person_name(api_get_setting('administratorName'), api_get_setting('administratorSurname'))."\n".
2600
                    get_lang('Manager')." ".api_get_setting('siteName')."\nT. ".
2601
                    api_get_setting('administratorTelephone')."\n".get_lang('Email')." : ".api_get_setting('emailAdministrator');
2602
2603
                api_mail_html(
2604
                    api_get_person_name($user['FirstName'], $user['LastName'], null, PERSON_NAME_EMAIL_ADDRESS),
2605
                    $user['Email'],
2606
                    $emailsubject,
2607
                    $emailbody
2608
                );
2609
                $userInfo = api_get_user_info($user['id']);
2610
2611 View Code Duplication
                if (($user['added_at_platform'] == 1  && $user['added_at_session'] == 1) || $user['added_at_session'] == 1) {
2612
                    if ($user['added_at_platform'] == 1) {
2613
                        $addedto = get_lang('UserCreatedPlatform');
2614
                    } else  {
2615
                        $addedto = '          ';
2616
                    }
2617
2618
                    if ($user['added_at_session'] == 1) {
2619
                        $addedto .= get_lang('UserInSession');
2620
                    }
2621
                } else {
2622
                    $addedto = get_lang('UserNotAdded');
2623
                }
2624
2625
                $registered_users .= UserManager::getUserProfileLink($userInfo)." - ".$addedto.'<br />';
0 ignored issues
show
Security Bug introduced by
It seems like $userInfo defined by api_get_user_info($user['id']) on line 2609 can also be of type false; however, UserManager::getUserProfileLink() 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...
2626
            }
2627
        } else {
2628
            $i = 0;
2629
            foreach ($users as $index => $user) {
2630
                $userInfo = api_get_user_info($user['id']);
2631 View Code Duplication
                if (($user['added_at_platform'] == 1 && $user['added_at_session'] == 1) || $user['added_at_session'] == 1) {
2632
                    if ($user['added_at_platform'] == 1) {
2633
                        $addedto = get_lang('UserCreatedPlatform');
2634
                    } else {
2635
                        $addedto = '          ';
2636
                    }
2637
2638
                    if ($user['added_at_session'] == 1) {
2639
                        $addedto .= ' '.get_lang('UserInSession');
2640
                    }
2641
                } else {
2642
                    $addedto = get_lang('UserNotAdded');
2643
                }
2644
                $registered_users .= "<a href=\"../user/userInfo.php?uInfo=".$user['id']."\">".api_get_person_name($user['FirstName'], $user['LastName'])."</a> - ".$addedto.'<br />';
2645
            }
2646
        }
2647
2648
        header('Location: course.php?id_session='.$id_session.'&action=show_message&message='.urlencode($registered_users));
2649
        exit;
2650
    }
2651
2652
    /**
2653
     * Reads CSV-file.
2654
     * @param string $file Path to the CSV-file
2655
     * @return array All userinformation read from the file
2656
     */
2657 View Code Duplication
    function parse_csv_data($file) {
2658
        $users = Import :: csvToArray($file);
0 ignored issues
show
Deprecated Code introduced by
The method Import::csvToArray() has been deprecated with message: use cvs_reader instead

This method has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the method will be removed from the class and what other method or class to use instead.

Loading history...
2659
        foreach ($users as $index => $user) {
2660
            if (isset ($user['Courses'])) {
2661
                $user['Courses'] = explode('|', trim($user['Courses']));
2662
            }
2663
            $users[$index] = $user;
2664
        }
2665
        return $users;
2666
    }
2667
2668
    /**
2669
     * XML-parser: the handler at the beginning of element.
2670
     */
2671 View Code Duplication
    function element_start($parser, $data) {
2672
        $data = api_utf8_decode($data);
2673
        global $user;
2674
        global $current_tag;
2675
        switch ($data) {
2676
            case 'Contact' :
2677
                $user = array ();
2678
                break;
2679
            default :
0 ignored issues
show
Coding Style introduced by
There must be no space before the colon in a DEFAULT statement

As per the PSR-2 coding standard, there must not be a space in front of the colon in the default statement.

switch ($expr) {
    default : //wrong
        doSomething();
        break;
}

switch ($expr) {
    default: //right
        doSomething();
        break;
}

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

Loading history...
2680
                $current_tag = $data;
2681
        }
2682
    }
2683
2684
    /**
2685
     * XML-parser: the handler at the end of element.
2686
     */
2687
    function element_end($parser, $data) {
2688
        $data = api_utf8_decode($data);
2689
        global $user;
2690
        global $users;
2691
        global $current_value;
2692
        global $purification_option_for_usernames;
2693
        $user[$data] = $current_value;
2694
        switch ($data) {
2695
            case 'Contact' :
2696
                $user['UserName'] = UserManager::purify_username($user['UserName'], $purification_option_for_usernames);
2697
                $users[] = $user;
2698
                break;
2699
            default :
0 ignored issues
show
Coding Style introduced by
There must be no space before the colon in a DEFAULT statement

As per the PSR-2 coding standard, there must not be a space in front of the colon in the default statement.

switch ($expr) {
    default : //wrong
        doSomething();
        break;
}

switch ($expr) {
    default: //right
        doSomething();
        break;
}

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

Loading history...
2700
                $user[$data] = $current_value;
2701
                break;
2702
        }
2703
    }
2704
2705
    /**
2706
     * XML-parser: the handler for character data.
2707
     */
2708
    function character_data($parser, $data) {
2709
        $data = trim(api_utf8_decode($data));
2710
        global $current_value;
2711
        $current_value = $data;
2712
    }
2713
2714
    /**
2715
     * Reads XML-file.
2716
     * @param string $file Path to the XML-file
2717
     * @return array All userinformation read from the file
2718
     */
2719
    function parse_xml_data($file) {
2720
        global $current_tag;
2721
        global $current_value;
2722
        global $user;
2723
        global $users;
2724
        $users = array ();
2725
        $parser = xml_parser_create('UTF-8');
2726
        xml_set_element_handler($parser, array('MySpace','element_start'), array('MySpace','element_end'));
2727
        xml_set_character_data_handler($parser, "character_data");
2728
        xml_parser_set_option($parser, XML_OPTION_CASE_FOLDING, false);
2729
        xml_parse($parser, api_utf8_encode_xml(file_get_contents($file)));
2730
        xml_parser_free($parser);
2731
        return $users;
2732
    }
2733
2734
    public static function displayTrackingAccessOverView($courseId, $sessionId, $studentId)
2735
    {
2736
        $courseId = intval($courseId);
2737
        $sessionId = intval($sessionId);
2738
        $studentId = intval($studentId);
2739
2740
        $em = Database::getManager();
2741
        $sessionRepo = $em->getRepository('ChamiloCoreBundle:Session');
2742
2743
        $courseList = [];
2744
        $sessionList = [];
2745
        $studentList = [];
2746
2747
        if (!empty($courseId)) {
2748
            $course = $em->find('ChamiloCoreBundle:Course', $courseId);
2749
2750
            $courseList[$course->getId()] = $course->getTitle();
2751
        }
2752
2753
        if (!empty($sessionId)) {
2754
            $session = $em->find('ChamiloCoreBundle:Session', $sessionId);
2755
2756
            $sessionList[$session->getId()] = $session->getName();
2757
        }
2758
2759
        if (!empty($studentId)) {
2760
            $student = $em->find('ChamiloUserBundle:User', $studentId);
2761
2762
            $studentList[$student->getId()] = $student->getCompleteName();
2763
        }
2764
2765
        $form = new FormValidator('access_overview', 'GET');
2766
        $form->addElement(
2767
            'select_ajax',
2768
            'course_id',
2769
            get_lang('SearchCourse'),
2770
            $courseList,
2771
            [
2772
                'url' => api_get_path(WEB_AJAX_PATH) . 'course.ajax.php?' . http_build_query([
2773
                    'a' => 'search_course_by_session_all',
2774
                    'session_id' => $sessionId
2775
                ])
2776
            ]
2777
        );
2778
        $form->addElement(
2779
            'select_ajax',
2780
            'session_id',
2781
            get_lang('SearchSession'),
2782
            $sessionList,
2783
            [
2784
                'url_function' => "
2785
                    function () {
2786
                        var params = $.param({
2787
                            a: 'search_session_by_course',
2788
                            course_id: $('#course_id').val() || 0
2789
                        });
2790
2791
                        return '" . api_get_path(WEB_AJAX_PATH) . "session.ajax.php?' + params;
2792
                    }
2793
                "
2794
            ]
2795
        );
2796
        $form->addSelect(
2797
            'profile',
2798
            get_lang('Profile'),
2799
            [
2800
                '' => get_lang('Select'),
2801
                STUDENT => get_lang('Student'),
2802
                COURSEMANAGER => get_lang('CourseManager'),
2803
                DRH => get_lang('Drh')
2804
            ],
2805
            ['id' => 'profile']
2806
        );
2807
        $form->addElement(
2808
            'select_ajax',
2809
            'student_id',
2810
            get_lang('SearchUsers'),
2811
            $studentList,
2812
            [
2813
                'placeholder' => get_lang('All'),
2814
                'url_function' => "
2815
                    function () {
2816
                        var params = $.param({
2817
                            a: 'search_user_by_course',
2818
                            session_id: $('#session_id').val(),
2819
                            course_id: $('#course_id').val()
2820
                        });
2821
2822
                        return '" . api_get_path(WEB_AJAX_PATH) . "course.ajax.php?' + params;
2823
                    }
2824
                "
2825
            ]
2826
        );
2827
        $form->addDateRangePicker(
2828
            'date',
2829
            get_lang('DateRange'),
2830
            true,
2831
            [
2832
                'id' => 'date_range',
2833
                'format' => 'YYYY-MM-DD',
2834
                'timePicker' => 'false',
2835
                'validate_format' => 'Y-m-d'
2836
            ]
2837
        );
2838
        $form->addHidden('display', 'accessoverview');
2839
        $form->addRule('course_id', get_lang('Required'), 'required');
2840
        $form->addRule('profile', get_lang('Required'), 'required');
2841
        $form->addButton('submit', get_lang('Generate'), 'gear', 'primary');
2842
2843
        $table = null;
2844
2845
        if ($form->validate()) {
2846
            $table = new SortableTable(
2847
                'tracking_access_overview',
2848
                ['MySpace','getNumberOfRrackingAccessOverview'],
2849
                ['MySpace','getUserDataAccessTrackingOverview'],
2850
                0
2851
            );
2852
            $table->additional_parameters = $form->exportValues();
2853
2854
            $table->set_header(0, get_lang('LoginDate'), true);
2855
            $table->set_header(1, get_lang('Username'), true);
2856 View Code Duplication
            if (api_is_western_name_order()) {
2857
                $table->set_header(2, get_lang('FirstName'), true);
2858
                $table->set_header(3, get_lang('LastName'), true);
2859
            } else {
2860
                $table->set_header(2, get_lang('LastName'), true);
2861
                $table->set_header(3, get_lang('FirstName'), true);
2862
            }
2863
            $table->set_header(4, get_lang('Clicks'), false);
2864
            $table->set_header(5, get_lang('IP'), false);
2865
            $table->set_header(6, get_lang('TimeLoggedIn'), false);
2866
        }
2867
2868
        $template = new Template(null, false, false, false, false, false, false);
2869
        $template->assign('form', $form->returnForm());
2870
        $template->assign('table', $table ? $table->return_table() : null);
2871
2872
        echo $template->fetch(
2873
            $template->get_template('my_space/accessoverview.tpl')
2874
        );
2875
    }
2876
2877
    public static function getNumberOfRrackingAccessOverview()
2878
    {
2879
        $track_e_course_access = Database::get_main_table(TABLE_STATISTIC_TRACK_E_COURSE_ACCESS);
2880
2881
        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...
2882
    }
2883
2884
    public static function getUserDataAccessTrackingOverview($from, $numberItems, $column, $orderDirection)
2885
    {
2886
        $user = Database::get_main_table(TABLE_MAIN_USER);
2887
        $course = Database::get_main_table(TABLE_MAIN_COURSE);
2888
        $track_e_login = Database::get_main_table(TABLE_STATISTIC_TRACK_E_LOGIN);
2889
        $track_e_course_access = Database::get_main_table(TABLE_STATISTIC_TRACK_E_COURSE_ACCESS);
2890
2891
        global $export_csv;
2892
2893
        if ($export_csv) {
2894
            $is_western_name_order = api_is_western_name_order(PERSON_NAME_DATA_EXPORT);
2895
        } else {
2896
            $is_western_name_order = api_is_western_name_order();
2897
        }
2898
2899
        //TODO add course name
2900
        $sql = "SELECT
2901
                a.login_course_date as col0,
2902
                u.username as col1,
2903
                " . (
2904
                    $is_western_name_order ? "
2905
                        u.firstname AS col2,
2906
                        u.lastname AS col3,
2907
                    " : "
2908
                        u.lastname AS col2,
2909
                        u.firstname AS col3,
2910
                " ) . "
2911
                a.logout_course_date,
2912
                c.title,
2913
                c.code,
2914
                u.user_id
2915
            FROM $track_e_course_access a
2916
            INNER JOIN $user u ON a.user_id = u.user_id
2917
            INNER JOIN $course c ON a.c_id = c.id";
2918
2919
        if (isset($_GET['session_id']) && !empty($_GET['session_id'])) {
2920
            $sessionId = intval($_GET['session_id']);
2921
            $sql .= " WHERE a.session_id = " . $sessionId;
2922
        }
2923
2924
        $sql .= " ORDER BY col$column $orderDirection ";
2925
        $sql .= " LIMIT $from,$numberItems";
2926
        $result = Database::query($sql);
2927
2928
        //$clicks = Tracking::get_total_clicks_by_session();
2929
        $data = array();
2930
2931
        while ($user = Database::fetch_assoc($result)) {
2932
            $data[] = $user;
2933
        }
2934
2935
        $return = [];
2936
2937
        //TODO: Dont use numeric index
2938
        foreach ($data as $key => $info) {
2939
            $start_date = $info['col0'];
2940
2941
            $end_date = $info['logout_course_date'];
2942
2943
            $return[$info['user_id']] = array(
2944
                $start_date,
2945
                $info['col1'],
2946
                $info['col2'],
2947
                $info['col3'],
2948
                $info['user_id'],
2949
                'ip',
2950
                //TODO is not correct/precise, it counts the time not logged between two loggins
2951
                gmdate("H:i:s", strtotime($end_date) - strtotime($start_date))
2952
            );
2953
        }
2954
2955
        foreach ($return as $key => $info) {
2956
            $ipResult = Database::select(
2957
                'user_ip',
2958
                $track_e_login,
2959
                ['where' => [
2960
                    '? BETWEEN login_date AND logout_date' => $info[0]
2961
                ]],
2962
                'first'
2963
            );
2964
2965
            $return[$key][5] = $ipResult['user_ip'];
2966
        }
2967
2968
        return $return;
2969
    }
2970
2971
    /**
2972
     * Gets the connections to a course as an array of login and logout time
2973
     *
2974
     * @param   int       $user_id
2975
     * @param   int    $courseId
2976
     * @author  Jorge Frisancho Jibaja
2977
     * @author  Julio Montoya <[email protected]> fixing the function
2978
     * @version OCT-22- 2010
2979
     * @return  array
2980
     */
2981
    public static function get_connections_to_course_by_date($user_id, $courseId, $start_date, $end_date)
2982
    {
2983
        // Database table definitions
2984
        $tbl_track_course = Database::get_main_table(TABLE_STATISTIC_TRACK_E_COURSE_ACCESS);
2985
        $course_info = api_get_course_info_by_id($courseId);
2986
        $user_id = intval($user_id);
2987
        $courseId = intval($courseId);
2988
        $connections = array();
2989
2990
        if (!empty($course_info)) {
2991
            $end_date = add_day_to($end_date);
2992
            $sql = "SELECT login_course_date, logout_course_date
2993
                FROM $tbl_track_course
2994
                WHERE
2995
                    user_id = $user_id AND
2996
                    c_id = $courseId AND
2997
                    login_course_date BETWEEN '$start_date' AND '$end_date' AND
2998
                    logout_course_date BETWEEN '$start_date' AND '$end_date'
2999
                ORDER BY login_course_date ASC";
3000
            $rs = Database::query($sql);
3001
3002
            while ($row = Database::fetch_array($rs)) {
3003
                $login_date = $row['login_course_date'];
3004
                $logout_date = $row['logout_course_date'];
3005
                $timestamp_login_date = strtotime($login_date);
3006
                $timestamp_logout_date = strtotime($logout_date);
3007
                $connections[] = array(
3008
                    'login' => $timestamp_login_date,
3009
                    'logout' => $timestamp_logout_date
3010
                );
3011
            }
3012
        }
3013
        return $connections;
3014
    }
3015
}
3016
3017
/**
3018
 * @param $user_id
3019
 * @param int $courseId
3020
 * @param null $start_date
3021
 * @param null $end_date
3022
 * @return array
3023
 */
3024
function get_stats($user_id, $courseId, $start_date = null, $end_date = null)
3025
{
3026
    // Database table definitions
3027
    $tbl_track_course   = Database :: get_main_table(TABLE_STATISTIC_TRACK_E_COURSE_ACCESS);
3028
3029
    $course_info = api_get_course_info_by_id($courseId);
3030
    if (!empty($course_info)) {
3031
        $strg_sd    = "";
3032
        $strg_ed    = "";
3033
        if ($start_date != null && $end_date != null){
3034
            $end_date = add_day_to( $end_date );
3035
            $strg_sd = "AND login_course_date BETWEEN '$start_date' AND '$end_date'";
3036
            $strg_ed = "AND logout_course_date BETWEEN '$start_date' AND '$end_date'";
3037
        }
3038
        $sql = 'SELECT
3039
                SEC_TO_TIME(avg(time_to_sec(timediff(logout_course_date,login_course_date)))) as avrg,
3040
                SEC_TO_TIME(sum(time_to_sec(timediff(logout_course_date,login_course_date)))) as total,
3041
                count(user_id) as times
3042
                FROM ' . $tbl_track_course . '
3043
                WHERE
3044
                    user_id = ' . intval($user_id) . ' AND
3045
                    c_id = ' . intval($courseId) . ' '.$strg_sd.' '.$strg_ed.' '.'
3046
                ORDER BY login_course_date ASC';
3047
3048
        $rs = Database::query($sql);
3049
        $result = array();
3050
3051
        if ($row = Database::fetch_array($rs)) {
3052
            $foo_avg    = $row['avrg'];
3053
            $foo_total  = $row['total'];
3054
            $foo_times  = $row['times'];
3055
            $result = array('avg' => $foo_avg, 'total' => $foo_total, 'times' => $foo_times);
3056
        }
3057
    }
3058
3059
    return $result;
3060
}
3061
3062
function add_day_to($end_date) {
3063
    $foo_date = strtotime( $end_date );
3064
    $foo_date = strtotime(" +1 day", $foo_date);
3065
    $foo_date = date("Y-m-d", $foo_date);
3066
    return $foo_date;
3067
}
3068
3069
/**
3070
 *
3071
 *
3072
 * @param array
3073
 * @author Jorge Frisancho Jibaja
3074
 * @version OCT-22- 2010
3075
 * @return array
3076
 */
3077 View Code Duplication
function convert_to_array($sql_result){
3078
    $result_to_print = '<table>';
3079
    foreach ($sql_result as $key => $data) {
3080
        $result_to_print .= '<tr><td>'.date('d-m-Y (H:i:s)', $data['login']).'</td><td>'.api_time_to_hms($data['logout'] - $data['login']).'</tr></td>'."\n";
3081
    }
3082
    $result_to_print .= '</table>';
3083
    $result_to_print = array("result"=>$result_to_print);
3084
    return $result_to_print;
3085
}
3086
3087
3088
/**
3089
 * Converte an array to a table in html
3090
 *
3091
 * @param array $sql_result
3092
 * @author Jorge Frisancho Jibaja
3093
 * @version OCT-22- 2010
3094
 * @return string
3095
 */
3096 View Code Duplication
function convert_to_string($sql_result){
3097
    $result_to_print = '<table>';
3098
    if (!empty($sql_result)) {
3099
        foreach ($sql_result as $key => $data) {
3100
            $result_to_print .= '<tr><td>'.date('d-m-Y (H:i:s)', $data['login']).'</td><td>'.api_time_to_hms($data['logout'] - $data['login']).'</tr></td>'."\n";
3101
        }
3102
    }
3103
    $result_to_print .= '</table>';
3104
    return $result_to_print;
3105
}
3106
3107
3108
/**
3109
 * This function draw the graphic to be displayed on the user view as an image
3110
 *
3111
 * @param array $sql_result
3112
 * @param string $start_date
3113
 * @param string $end_date
3114
 * @param string $type
3115
 * @author Jorge Frisancho Jibaja
3116
 * @version OCT-22- 2010
3117
 * @return string
3118
 */
3119
function grapher($sql_result, $start_date, $end_date, $type = "")
3120
{
3121
    if (empty($start_date)) { $start_date =""; }
3122
    if (empty($end_date)) { $end_date =""; }
3123
    if ($type == ""){ $type = 'day'; }
3124
    $main_year  = $main_month_year = $main_day = array();
3125
    // get last 8 days/months
3126
    $last_days      = 5;
3127
    $last_months    = 3;
3128
    for ($i = $last_days; $i >= 0; $i--) {
3129
        $main_day[date ('d-m-Y', mktime () - $i * 3600 * 24)] = 0;
3130
    }
3131
    for ($i = $last_months; $i >= 0; $i--) {
3132
        $main_month_year[date ('m-Y', mktime () - $i * 30 * 3600 * 24)] = 0;
3133
    }
3134
3135
    $i = 0;
3136
    if (is_array($sql_result) && count($sql_result) > 0) {
3137
        foreach ($sql_result as $key => $data) {
3138
            //creating the main array
3139
            $main_month_year[date('m-Y', $data['login'])] += float_format(($data['logout'] - $data['login']) / 60, 0);
3140
            $main_day[date('d-m-Y', $data['login'])] += float_format(($data['logout'] - $data['login']) / 60, 0);
3141
            if ($i > 500) {
3142
                break;
3143
            }
3144
            $i++;
3145
        }
3146
        switch ($type) {
3147
            case 'day':
3148
                $main_date = $main_day;
3149
                break;
3150
            case 'month':
3151
                $main_date = $main_month_year;
3152
                break;
3153
            case 'year':
3154
                $main_date = $main_year;
3155
                break;
3156
        }
3157
3158
        // the nice graphics :D
3159
        $labels = array_keys($main_date);
3160
        if (count($main_date) == 1) {
3161
            $labels = $labels[0];
3162
            $main_date = $main_date[$labels];
3163
        }
3164
3165
        /* Create and populate the pData object */
3166
        $myData = new pData();
3167
        $myData->addPoints($main_date, 'Serie1');
3168
        if (count($main_date)!= 1) {
3169
            $myData->addPoints($labels, 'Labels');
3170
            $myData->setSerieDescription('Labels', 'Months');
3171
            $myData->setAbscissa('Labels');
3172
        }
3173
        $myData->setSerieWeight('Serie1', 1);
3174
        $myData->setSerieDescription('Serie1', get_lang('MyResults'));
3175
        $myData->setAxisName(0, get_lang('Minutes'));
3176
        $myData->loadPalette(api_get_path(SYS_CODE_PATH) . 'palettes/pchart/default.color', true);
3177
3178
        // Cache definition
3179
        $cachePath = api_get_path(SYS_ARCHIVE_PATH);
3180
        $myCache = new pCache(array('CacheFolder' => substr($cachePath, 0, strlen($cachePath) - 1)));
3181
        $chartHash = $myCache->getHash($myData);
3182
3183
        if ($myCache->isInCache($chartHash)) {
3184
            //if we already created the img
3185
            $imgPath = api_get_path(SYS_ARCHIVE_PATH) . $chartHash;
3186
            $myCache->saveFromCache($chartHash, $imgPath);
3187
            $imgPath = api_get_path(WEB_ARCHIVE_PATH) . $chartHash;
3188
        } else {
3189
            /* Define width, height and angle */
3190
            $mainWidth = 760;
3191
            $mainHeight = 230;
3192
            $angle = 50;
3193
3194
            /* Create the pChart object */
3195
            $myPicture = new pImage($mainWidth, $mainHeight, $myData);
3196
3197
            /* Turn of Antialiasing */
3198
            $myPicture->Antialias = false;
3199
3200
            /* Draw the background */
3201
            $settings = array("R" => 255, "G" => 255, "B" => 255);
3202
            $myPicture->drawFilledRectangle(0, 0, $mainWidth, $mainHeight, $settings);
3203
3204
            /* Add a border to the picture */
3205
            $myPicture->drawRectangle(
3206
                0,
3207
                0,
3208
                $mainWidth - 1,
3209
                $mainHeight - 1,
3210
                array("R" => 0, "G" => 0, "B" => 0)
3211
            );
3212
3213
            /* Set the default font */
3214
            $myPicture->setFontProperties(
3215
                array(
3216
                    "FontName" => api_get_path(SYS_FONTS_PATH) . 'opensans/OpenSans-Regular.ttf',
3217
                    "FontSize" => 10)
3218
            );
3219
            /* Write the chart title */
3220
            $myPicture->drawText(
3221
                $mainWidth / 2,
3222
                30,
3223
                get_lang('ExercisesInTimeProgressChart'),
3224
                array(
3225
                    "FontSize" => 12,
3226
                    "Align" => TEXT_ALIGN_BOTTOMMIDDLE
3227
                )
3228
            );
3229
3230
            /* Set the default font */
3231
            $myPicture->setFontProperties(
3232
                array(
3233
                    "FontName" => api_get_path(SYS_FONTS_PATH) . 'opensans/OpenSans-Regular.ttf',
3234
                    "FontSize" => 8
3235
                )
3236
            );
3237
3238
            /* Define the chart area */
3239
            $myPicture->setGraphArea(50, 40, $mainWidth - 40, $mainHeight - 80);
3240
3241
            /* Draw the scale */
3242
            $scaleSettings = array(
3243
                'XMargin' => 10,
3244
                'YMargin' => 10,
3245
                'Floating' => true,
3246
                'GridR' => 200,
3247
                'GridG' => 200,
3248
                'GridB' => 200,
3249
                'DrawSubTicks' => true,
3250
                'CycleBackground' => true,
3251
                'LabelRotation' => $angle,
3252
                'Mode' => SCALE_MODE_ADDALL_START0,
3253
            );
3254
            $myPicture->drawScale($scaleSettings);
3255
3256
            /* Turn on Antialiasing */
3257
            $myPicture->Antialias = true;
3258
3259
            /* Enable shadow computing */
3260
            $myPicture->setShadow(
3261
                true,
3262
                array(
3263
                    "X" => 1,
3264
                    "Y" => 1,
3265
                    "R" => 0,
3266
                    "G" => 0,
3267
                    "B" => 0,
3268
                    "Alpha" => 10
3269
                )
3270
            );
3271
3272
            /* Draw the line chart */
3273
            $myPicture->setFontProperties(
3274
                array(
3275
                    "FontName" => api_get_path(SYS_FONTS_PATH) . 'opensans/OpenSans-Regular.ttf',
3276
                    "FontSize" => 10
3277
                )
3278
            );
3279
            $myPicture->drawSplineChart();
3280
            $myPicture->drawPlotChart(
3281
                array(
3282
                    "DisplayValues" => true,
3283
                    "PlotBorder" => true,
3284
                    "BorderSize" => 1,
3285
                    "Surrounding" => -60,
3286
                    "BorderAlpha" => 80
3287
                )
3288
            );
3289
3290
            /* Do NOT Write the chart legend */
3291
3292
            /* Write and save into cache */
3293
            $myCache->writeToCache($chartHash, $myPicture);
3294
            $imgPath = api_get_path(SYS_ARCHIVE_PATH) . $chartHash;
3295
            $myCache->saveFromCache($chartHash, $imgPath);
3296
            $imgPath = api_get_path(WEB_ARCHIVE_PATH) . $chartHash;
3297
        }
3298
        $html = '<img src="' . $imgPath . '">';
3299
3300
        return $html;
3301
    } else {
3302
        $foo_img = api_convert_encoding('<div id="messages" class="warning-message">'.get_lang('GraphicNotAvailable').'</div>','UTF-8');
3303
3304
        return $foo_img;
3305
    }
3306
}
3307