Passed
Push — master ( c90ddc...3681fe )
by Julito
12:04
created

AddCourse::insertDocument()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 15
Code Lines 9

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
eloc 9
c 0
b 0
f 0
nc 1
nop 4
dl 0
loc 15
rs 9.9666
1
<?php
2
/* For licensing terms, see /license.txt */
3
4
use Chamilo\CoreBundle\Entity\Course;
5
use Chamilo\CoreBundle\Entity\CourseRelUser;
6
use Chamilo\CoreBundle\Framework\Container;
7
use Chamilo\CourseBundle\Entity\CGroupCategory;
8
use Chamilo\CourseBundle\Entity\CToolIntro;
9
10
/**
11
 * Class AddCourse.
12
 */
13
class AddCourse
14
{
15
    public const FIRST_EXPIRATION_DATE = 31536000; // 365 days in seconds
16
17
    /**
18
     * Defines the four needed keys to create a course based on several parameters.
19
     *
20
     * @param string    The code you want for this course
21
     * @param string    Prefix added for ALL keys
22
     * @param string    Prefix added for databases only
23
     * @param string    Prefix added for paths only
24
     * @param bool      Add unique prefix
25
     * @param bool      Use code-independent keys
26
     *
27
     * @return array An array with the needed keys ['currentCourseCode'], ['currentCourseId'], ['currentCourseDbName'],
28
     *               ['currentCourseRepository']
29
     *
30
     * @todo Eliminate the global variables.
31
     * @assert (null) === false
32
     */
33
    public static function define_course_keys(
34
        $wanted_code,
35
        $prefix_for_all = '',
36
        $prefix_for_base_name = '',
37
        $prefix_for_path = '',
38
        $add_unique_prefix = false,
39
        $use_code_indepedent_keys = true
40
    ) {
41
        $course_table = Database::get_main_table(TABLE_MAIN_COURSE);
42
        $wanted_code = CourseManager::generate_course_code($wanted_code);
43
        $keys_course_code = $wanted_code;
44
        if (!$use_code_indepedent_keys) {
45
            $wanted_code = '';
46
        }
47
48
        $unique_prefix = '';
49
        if ($add_unique_prefix) {
50
            $unique_prefix = substr(md5(uniqid(rand())), 0, 10);
51
        }
52
53
        $keys = [];
54
        $final_suffix = ['CourseId' => '', 'CourseDb' => '', 'CourseDir' => ''];
55
        $limit_numb_try = 100;
56
        $keys_are_unique = false;
57
        $try_new_fsc_id = $try_new_fsc_db = $try_new_fsc_dir = 0;
58
59
        while (!$keys_are_unique) {
60
            $keys_course_id = $prefix_for_all.$unique_prefix.$wanted_code.$final_suffix['CourseId'];
61
            $keys_course_repository = $prefix_for_path.$unique_prefix.$wanted_code.$final_suffix['CourseDir'];
62
            $keys_are_unique = true;
63
64
            // Check whether they are unique.
65
            $query = "SELECT 1 FROM $course_table
66
                      WHERE code='".$keys_course_id."'
67
                      LIMIT 0, 1";
68
            $result = Database::query($query);
69
70
            if (Database::num_rows($result)) {
71
                $keys_are_unique = false;
72
                $try_new_fsc_id++;
73
                $final_suffix['CourseId'] = substr(md5(uniqid(rand())), 0, 4);
74
            }
75
76
            if (($try_new_fsc_id + $try_new_fsc_db + $try_new_fsc_dir) > $limit_numb_try) {
77
                return $keys;
78
            }
79
        }
80
81
        $keys['currentCourseCode'] = $keys_course_code;
82
        $keys['currentCourseId'] = $keys_course_id;
83
        $keys['currentCourseRepository'] = $keys_course_repository;
84
85
        return $keys;
86
    }
87
88
    /**
89
     * Gets an array with all the course tables (deprecated?).
90
     *
91
     * @return array
92
     *
93
     * @assert (null) !== null
94
     */
95
    public static function get_course_tables()
96
    {
97
        $tables = [];
98
        //$tables[] = 'item_property';
99
        $tables[] = 'tool';
100
        $tables[] = 'tool_intro';
101
        $tables[] = 'group_info';
102
        $tables[] = 'group_category';
103
        $tables[] = 'group_rel_user';
104
        $tables[] = 'group_rel_tutor';
105
        $tables[] = 'userinfo_content';
106
        $tables[] = 'userinfo_def';
107
        $tables[] = 'course_description';
108
        $tables[] = 'calendar_event';
109
        $tables[] = 'calendar_event_repeat';
110
        $tables[] = 'calendar_event_repeat_not';
111
        $tables[] = 'calendar_event_attachment';
112
        $tables[] = 'announcement';
113
        $tables[] = 'announcement_attachment';
114
        //$tables[] = 'resource';
115
        $tables[] = 'student_publication';
116
        $tables[] = 'student_publication_assignment';
117
        $tables[] = 'document';
118
        /*$tables[] = 'forum_category';
119
        $tables[] = 'forum_forum';
120
        $tables[] = 'forum_thread';
121
        $tables[] = 'forum_post';
122
        $tables[] = 'forum_mailcue';
123
        $tables[] = 'forum_attachment';
124
        $tables[] = 'forum_notification';
125
        $tables[] = 'forum_thread_qualify';
126
        $tables[] = 'forum_thread_qualify_log';*/
127
        $tables[] = 'link';
128
        $tables[] = 'link_category';
129
        $tables[] = 'online_connected';
130
        $tables[] = 'online_link';
131
        $tables[] = 'chat_connected';
132
        $tables[] = 'quiz';
133
        $tables[] = 'quiz_rel_question';
134
        $tables[] = 'quiz_question';
135
        $tables[] = 'quiz_answer';
136
        $tables[] = 'quiz_question_option';
137
        $tables[] = 'quiz_question_category';
138
        $tables[] = 'quiz_question_rel_category';
139
        $tables[] = 'dropbox_post';
140
        $tables[] = 'dropbox_file';
141
        $tables[] = 'dropbox_person';
142
        $tables[] = 'dropbox_category';
143
        $tables[] = 'dropbox_feedback';
144
        $tables[] = 'lp';
145
        $tables[] = 'lp_item';
146
        $tables[] = 'lp_view';
147
        $tables[] = 'lp_item_view';
148
        $tables[] = 'lp_iv_interaction';
149
        $tables[] = 'lp_iv_objective';
150
        $tables[] = 'blog';
151
        $tables[] = 'blog_comment';
152
        $tables[] = 'blog_post';
153
        $tables[] = 'blog_rating';
154
        $tables[] = 'blog_rel_user';
155
        $tables[] = 'blog_task';
156
        $tables[] = 'blog_task_rel_user';
157
        $tables[] = 'blog_attachment';
158
        $tables[] = 'permission_group';
159
        $tables[] = 'permission_user';
160
        $tables[] = 'permission_task';
161
        $tables[] = 'role';
162
        $tables[] = 'role_group';
163
        $tables[] = 'role_permissions';
164
        $tables[] = 'role_user';
165
        $tables[] = 'survey';
166
        $tables[] = 'survey_question';
167
        $tables[] = 'survey_question_option';
168
        $tables[] = 'survey_invitation';
169
        $tables[] = 'survey_answer';
170
        $tables[] = 'survey_group';
171
        $tables[] = 'wiki';
172
        $tables[] = 'wiki_conf';
173
        $tables[] = 'wiki_discuss';
174
        $tables[] = 'wiki_mailcue';
175
        $tables[] = 'course_setting';
176
        $tables[] = 'glossary';
177
        $tables[] = 'notebook';
178
        $tables[] = 'attendance';
179
        $tables[] = 'attendance_sheet';
180
        $tables[] = 'attendance_calendar';
181
        $tables[] = 'attendance_result';
182
        $tables[] = 'attendance_sheet_log';
183
        $tables[] = 'thematic';
184
        $tables[] = 'thematic_plan';
185
        $tables[] = 'thematic_advance';
186
187
        return $tables;
188
    }
189
190
    /**
191
     * Executed only before create_course_tables().
192
     *
193
     * @assert (null) === null
194
     */
195
    public static function drop_course_tables()
196
    {
197
        $list = self::get_course_tables();
198
        foreach ($list as $table) {
199
            $sql = "DROP TABLE IF EXISTS ".DB_COURSE_PREFIX.$table;
200
            Database::query($sql);
201
        }
202
    }
203
204
    /**
205
     * Sorts pictures by type (used?).
206
     *
207
     * @param array List of files (sthg like array(0=>array('png'=>1)))
208
     * @param string $type
209
     *
210
     * @return array The received array without files not matching type
211
     * @assert (array(),null) === array()
212
     */
213
    public static function sort_pictures($files, $type)
214
    {
215
        $pictures = [];
216
        foreach ($files as $value) {
217
            if (isset($value[$type]) && '' != $value[$type]) {
218
                $pictures[][$type] = $value[$type];
219
            }
220
        }
221
222
        return $pictures;
223
    }
224
225
    /**
226
     * Fills the course database with some required content and example content.
227
     *
228
     * @param array $courseInfo
229
     * @param bool Whether to fill the course with example content
230
     * @param int $authorId
231
     *
232
     * @return bool False on error, true otherwise
233
     *
234
     * @version 1.2
235
     * @assert (null, '', '', null) === false
236
     * @assert (1, 'ABC', null, null) === false
237
     * @assert (1, 'TEST', 'spanish', true) === true
238
     */
239
    public static function fillCourse(
240
        $courseInfo,
241
        $fill_with_exemplary_content = null,
242
        $authorId = 0
243
    ) {
244
        if (is_null($fill_with_exemplary_content)) {
245
            $fill_with_exemplary_content = 'false' !== api_get_setting('example_material_course_creation');
246
        }
247
248
        $course_id = (int) $courseInfo['real_id'];
249
250
        if (empty($courseInfo)) {
251
            return false;
252
        }
253
        $authorId = empty($authorId) ? api_get_user_id() : (int) $authorId;
254
255
        $TABLEGROUPCATEGORIES = Database::get_course_table(TABLE_GROUP_CATEGORY);
256
        $TABLESETTING = Database::get_course_table(TABLE_COURSE_SETTING);
257
        $TABLEGRADEBOOK = Database::get_main_table(TABLE_MAIN_GRADEBOOK_CATEGORY);
258
        $TABLEGRADEBOOKLINK = Database::get_main_table(TABLE_MAIN_GRADEBOOK_LINK);
259
        $course = api_get_course_entity($course_id);
260
        $settingsManager = CourseManager::getCourseSettingsManager();
261
        $settingsManager->setCourse($course);
262
263
        $alert = api_get_setting('email_alert_manager_on_new_quiz');
264
        $defaultEmailExerciseAlert = 0;
265
        if ('true' === $alert) {
266
            $defaultEmailExerciseAlert = 1;
267
        }
268
269
        /* course_setting table (courseinfo tool)   */
270
        $settings = [
271
            'email_alert_manager_on_new_doc' => ['title' => '', 'default' => 0, 'category' => 'work'],
272
            'email_alert_on_new_doc_dropbox' => ['default' => 0, 'category' => 'dropbox'],
273
            'allow_user_edit_agenda' => ['default' => 0, 'category' => 'agenda'],
274
            'allow_user_edit_announcement' => ['default' => 0, 'category' => 'announcement'],
275
            'email_alert_manager_on_new_quiz' => ['default' => $defaultEmailExerciseAlert, 'category' => 'quiz'],
276
            'allow_user_image_forum' => ['default' => 1, 'category' => 'forum'],
277
            'course_theme' => ['default' => '', 'category' => 'theme'],
278
            'allow_learning_path_theme' => ['default' => 1, 'category' => 'theme'],
279
            'allow_open_chat_window' => ['default' => 1, 'category' => 'chat'],
280
            'email_alert_to_teacher_on_new_user_in_course' => ['default' => 0, 'category' => 'registration'],
281
            'allow_user_view_user_list' => ['default' => 1, 'category' => 'user'],
282
            'display_info_advance_inside_homecourse' => ['default' => 1, 'category' => 'thematic_advance'],
283
            'email_alert_students_on_new_homework' => ['default' => 0, 'category' => 'work'],
284
            'enable_lp_auto_launch' => ['default' => 0, 'category' => 'learning_path'],
285
            'enable_exercise_auto_launch' => ['default' => 0, 'category' => 'exercise'],
286
            'enable_document_auto_launch' => ['default' => 0, 'category' => 'document'],
287
            'pdf_export_watermark_text' => ['default' => '', 'category' => 'learning_path'],
288
            'allow_public_certificates' => [
289
                'default' => 'true' === api_get_setting('allow_public_certificates') ? 1 : '',
290
                'category' => 'certificates',
291
            ],
292
            'documents_default_visibility' => ['default' => 'visible', 'category' => 'document'],
293
            'show_course_in_user_language' => ['default' => 2, 'category' => null],
294
            'email_to_teachers_on_new_work_feedback' => ['default' => 1, 'category' => null],
295
        ];
296
297
        $counter = 1;
298
        foreach ($settings as $variable => $setting) {
299
            $title = $setting['title'] ?? '';
300
            Database::query(
301
                "INSERT INTO $TABLESETTING (c_id, title, variable, value, category)
302
                      VALUES ($course_id, '".$title."', '".$variable."', '".$setting['default']."', '".$setting['category']."')"
303
            );
304
            $counter++;
305
        }
306
307
        /* Course homepage tools for platform admin only */
308
        /* Group tool */
309
        $groupCategory = new CGroupCategory();
310
        $groupCategory
311
            ->setTitle(get_lang('Default groups'))
312
            ->setParent($course)
313
            ->addCourseLink($course)
314
        ;
315
        Database::getManager()->persist($groupCategory);
316
317
        $now = api_get_utc_datetime();
318
        $files = [
319
            ['path' => '/shared_folder', 'title' => get_lang('Folders of users'), 'filetype' => 'folder', 'size' => 0],
320
            [
321
                'path' => '/chat_files',
322
                'title' => get_lang('Chat conversations history'),
323
                'filetype' => 'folder',
324
                'size' => 0,
325
            ],
326
            ['path' => '/certificates', 'title' => get_lang('Certificates'), 'filetype' => 'folder', 'size' => 0],
327
        ];
328
329
        $counter = 1;
330
        foreach ($files as $file) {
331
            self::insertDocument($courseInfo, $counter, $file, $authorId);
332
            $counter++;
333
        }
334
335
        $certificateId = 'NULL';
336
337
        /*    Documents   */
338
        if ($fill_with_exemplary_content) {
339
            $files = [
340
                ['path' => '/audio', 'title' => get_lang('Audio'), 'filetype' => 'folder', 'size' => 0],
341
                ['path' => '/flash', 'title' => get_lang('Flash'), 'filetype' => 'folder', 'size' => 0],
342
                ['path' => '/images', 'title' => get_lang('Images'), 'filetype' => 'folder', 'size' => 0],
343
                ['path' => '/images/diagrams', 'title' => get_lang('Diagrams'), 'filetype' => 'folder', 'size' => 0],
344
                ['path' => '/images/diagrams/animated', 'title' => 'animated', 'filetype' => 'folder', 'size' => 0],
345
                [
346
                    'path' => '/images/mr_chamilo',
347
                    'title' => get_lang('Mr Chamilo'),
348
                    'filetype' => 'folder',
349
                    'size' => 0,
350
                ],
351
                ['path' => '/images/mr_chamilo/svg', 'title' => 'svg', 'filetype' => 'folder', 'size' => 0],
352
                ['path' => '/images/small', 'title' => get_lang('Small'), 'filetype' => 'folder', 'size' => 0],
353
                ['path' => '/images/trainer', 'title' => get_lang('Trainer'), 'filetype' => 'folder', 'size' => 0],
354
                ['path' => '/images/gallery', 'title' => get_lang('Gallery'), 'filetype' => 'folder', 'size' => 0],
355
                ['path' => '/video', 'title' => get_lang('Video'), 'filetype' => 'folder', 'size' => 0],
356
                ['path' => '/video/flv', 'title' => 'flv', 'filetype' => 'folder', 'size' => 0],
357
            ];
358
            $paths = [];
359
            foreach ($files as $file) {
360
                $doc = self::insertDocument($courseInfo, $counter, $file, $authorId);
361
                $paths[$file['path']] = $doc->getIid();
362
                $counter++;
363
            }
364
365
            $finder = new Symfony\Component\Finder\Finder();
366
            $defaultPath = api_get_path(SYS_PUBLIC_PATH).'img/document';
367
            $finder->in($defaultPath);
368
369
            /** @var SplFileInfo $file */
370
            /*foreach ($finder as $file) {
371
                $parentName = dirname(str_replace($defaultPath, '', $file->getRealPath()));
372
                if ('/' === $parentName || '/certificates' === $parentName) {
373
                    continue;
374
                }
375
376
                $title = $file->getFilename();
377
                $parentId = $paths[$parentName];
378
379
                if ($file->isDir()) {
380
                    $realPath = str_replace($defaultPath, '', $file->getRealPath());
381
                    DocumentManager::addDocument(
382
                        $courseInfo,
383
                        $realPath,
384
                        'folder',
385
                        null,
386
                        $title,
387
                        '',
388
                        null,
389
                        null,
390
                        null,
391
                        null,
392
                        null,
393
                        false,
394
                        null,
395
                        $parentId,
396
                        $file->getRealPath()
397
                    );
398
                } else {
399
                    $realPath = str_replace($defaultPath, '', $file->getRealPath());
400
                    $document = DocumentManager::addDocument(
401
                        $courseInfo,
402
                        $realPath,
403
                        'file',
404
                        $file->getSize(),
405
                        $title,
406
                        '',
407
                        null,
408
                        null,
409
                        null,
410
                        null,
411
                        null,
412
                        false,
413
                        null,
414
                        $parentId,
415
                        $file->getRealPath()
416
                    );
417
418
                    if ($document && 'default.html' === $document->getTitle()) {
419
                        $certificateId = $document->getIid();
420
                    }
421
                }
422
            }*/
423
424
            $agenda = new Agenda('course');
425
            $agenda->set_course($courseInfo);
426
            $agenda->addEvent(
427
                $now,
428
                $now,
429
                0,
430
                get_lang('Course creation'),
431
                get_lang('This course was created at this time')
432
            );
433
434
            /*  Links tool */
435
            $link = new Link();
436
            $link->setCourse($courseInfo);
437
            $links = [
438
                [
439
                    'c_id' => $course_id,
440
                    'url' => 'http://www.google.com',
441
                    'title' => 'Quick and powerful search engine',
442
                    'description' => get_lang('Quick and powerful search engine'),
443
                    'category_id' => 0,
444
                    'on_homepage' => 0,
445
                    'target' => '_self',
446
                    'session_id' => 0,
447
                ],
448
                [
449
                    'c_id' => $course_id,
450
                    'url' => 'http://www.wikipedia.org',
451
                    'title' => 'Free online encyclopedia',
452
                    'description' => get_lang('Free online encyclopedia'),
453
                    'category_id' => 0,
454
                    'on_homepage' => 0,
455
                    'target' => '_self',
456
                    'session_id' => 0,
457
                ],
458
            ];
459
460
            foreach ($links as $params) {
461
                $link->save($params, false, false);
462
            }
463
464
            /* Announcement tool */
465
            AnnouncementManager::add_announcement(
466
                $courseInfo,
467
                0,
468
                get_lang('This is an announcement example'),
469
                get_lang('This is an announcement example. Only trainers are allowed to publish announcements.'),
470
                ['everyone' => 'everyone'],
471
                null,
472
                null,
473
                $now
474
            );
475
476
            $manager = Database::getManager();
477
478
            /* Introduction text */
479
            $intro_text = '<p style="text-align: center;">
480
                            <img src="'.api_get_path(REL_CODE_PATH).'img/mascot.png" alt="Mr. Chamilo" title="Mr. Chamilo" />
481
                            <h2>'.get_lang('Introduction text').'</h2>
482
                         </p>';
483
484
            $toolIntro = new CToolIntro();
485
            $toolIntro
486
                ->setCId($course_id)
487
                ->setSessionId(0)
488
                ->setIntroText($intro_text);
489
            $manager->persist($toolIntro);
490
491
            $toolIntro = new CToolIntro();
492
            $toolIntro
493
                ->setCId($course_id)
494
                ->setSessionId(0)
495
                ->setIntroText(get_lang('This page allows users and groups to publish documents.'));
496
            $manager->persist($toolIntro);
497
498
            $toolIntro = new CToolIntro();
499
            $toolIntro
500
                ->setCId($course_id)
501
                ->setSessionId(0)
502
                ->setIntroText(get_lang('The word Wiki is short for WikiWikiWeb. Wikiwiki is a Hawaiian word, meaning "fast" or "speed". In a wiki, people write pages together. If one person writes something wrong, the next person can correct it. The next person can also add something new to the page. Because of this, the pages improve continuously.'));
503
            $manager->persist($toolIntro);
504
505
            $manager->flush();
506
507
            /*  Exercise tool */
508
            $exercise = new Exercise($course_id);
509
            $exercise->exercise = get_lang('Sample test');
510
            $html = '<table width="100%" border="0" cellpadding="0" cellspacing="0">
511
                        <tr>
512
                        <td width="220" valign="top" align="left">
513
                            <img src="'.api_get_path(WEB_PUBLIC_PATH).'img/document/images/mr_chamilo/doubts.png">
514
                        </td>
515
                        <td valign="top" align="left">'.get_lang('Irony').'</td></tr>
516
                    </table>';
517
            $exercise->type = 1;
518
            $exercise->setRandom(0);
519
            $exercise->active = 1;
520
            $exercise->results_disabled = 0;
521
            $exercise->description = $html;
522
            $exercise->save();
523
524
            $exercise_id = $exercise->id;
525
526
            $question = new MultipleAnswer();
527
            $question->course = $courseInfo;
528
            $question->question = get_lang('Socratic irony is...');
529
            $question->description = get_lang('(more than one answer can be true)');
530
            $question->weighting = 10;
531
            $question->position = 1;
532
            $question->course = $courseInfo;
533
            $question->save($exercise);
534
            $questionId = $question->id;
535
536
            $answer = new Answer($questionId, $courseInfo['real_id']);
537
            $answer->createAnswer(get_lang('Ridiculise one\'s interlocutor in order to have him concede he is wrong.'), 0, get_lang('No. Socratic irony is not a matter of psychology, it concerns argumentation.'), -5, 1);
538
            $answer->createAnswer(get_lang('Admit one\'s own errors to invite one\'s interlocutor to do the same.'), 0, get_lang('No. Socratic irony is not a seduction strategy or a method based on the example.'), -5, 2);
539
            $answer->createAnswer(get_lang('Compell one\'s interlocutor, by a series of questions and sub-questions, to admit he doesn\'t know what he claims to know.'), 1, get_lang('Indeed'), 5, 3);
540
            $answer->createAnswer(get_lang('Use the Principle of Non Contradiction to force one\'s interlocutor into a dead end.'), 1, get_lang('This answer is not false. It is true that the revelation of the interlocutor\'s ignorance means showing the contradictory conclusions where lead his premisses.'), 5, 4);
541
            $answer->save();
542
543
            /* Forum tool */
544
            require_once api_get_path(SYS_CODE_PATH).'forum/forumfunction.inc.php';
545
546
            $params = [
547
                'forum_category_title' => get_lang('Example Forum Category'),
548
                'forum_category_comment' => '',
549
            ];
550
551
            $forumCategoryId = store_forumcategory($params, $courseInfo, false);
552
553
            $params = [
554
                'forum_category' => $forumCategoryId,
555
                'forum_title' => get_lang('Example Forum'),
556
                'forum_comment' => '',
557
                'default_view_type_group' => ['default_view_type' => 'flat'],
558
            ];
559
560
            $forumId = store_forum($params, $courseInfo, true);
561
            $repo = Container::getForumRepository();
562
            $forumEntity = $repo->find($forumId);
563
564
            $params = [
565
                'post_title' => get_lang('Example Thread'),
566
                'forum_id' => $forumId,
567
                'post_text' => get_lang('Example ThreadContent'),
568
                'calification_notebook_title' => '',
569
                'numeric_calification' => '',
570
                'weight_calification' => '',
571
                'forum_category' => $forumCategoryId,
572
                'thread_peer_qualify' => 0,
573
            ];
574
575
            store_thread($forumEntity, $params, $courseInfo, false);
576
577
            /* Gradebook tool */
578
            $course_code = $courseInfo['code'];
579
            // father gradebook
580
            Database::query(
581
                "INSERT INTO $TABLEGRADEBOOK (name, locked, generate_certificates, description, user_id, c_id, parent_id, weight, visible, certif_min_score, session_id, document_id)
582
                VALUES ('$course_code','0',0,'',1,$course_id,0,100,0,75,NULL,$certificateId)"
583
            );
584
            $gbid = Database:: insert_id();
585
            Database::query(
586
                "INSERT INTO $TABLEGRADEBOOK (name, locked, generate_certificates, description, user_id, c_id, parent_id, weight, visible, certif_min_score, session_id, document_id)
587
                VALUES ('$course_code','0',0,'',1,$course_id,$gbid,100,1,75,NULL,$certificateId)"
588
            );
589
            $gbid = Database:: insert_id();
590
            Database::query(
591
                "INSERT INTO $TABLEGRADEBOOKLINK (type, ref_id, user_id, c_id, category_id, created_at, weight, visible, locked)
592
                VALUES (1,$exercise_id,1,$course_id,$gbid,'$now',100,1,0)"
593
            );
594
        }
595
596
        // Installing plugins in course
597
        $app_plugin = new AppPlugin();
598
        $app_plugin->install_course_plugins($course_id);
599
600
        return true;
601
    }
602
603
    /**
604
     * @param array $courseInfo
605
     * @param int   $counter
606
     * @param array $file
607
     * @param int   $authorId
608
     */
609
    public static function insertDocument($courseInfo, $counter, $file, $authorId = 0)
610
    {
611
        return DocumentManager::addDocument(
612
            $courseInfo,
613
            $file['path'],
614
            $file['filetype'],
615
            $file['size'],
616
            $file['title'],
617
            null,
618
            0,
619
            null,
620
            0,
621
            0,
622
            0,
623
            false
624
        );
625
    }
626
627
    /**
628
     * string2binary converts the string "true" or "false" to the boolean true false (0 or 1)
629
     * This is used for the Chamilo Config Settings as these store true or false as string
630
     * and the api_get_setting('course_create_active_tools') should be 0 or 1 (used for
631
     * the visibility of the tool).
632
     *
633
     * @param string $variable
634
     *
635
     * @return bool
636
     *
637
     * @author Patrick Cool, [email protected]
638
     * @assert ('true') === true
639
     * @assert ('false') === false
640
     */
641
    public static function string2binary($variable)
642
    {
643
        if ('true' == $variable) {
644
            return true;
645
        }
646
        if ('false' == $variable) {
647
            return false;
648
        }
649
    }
650
651
    /**
652
     * Function register_course to create a record in the course table of the main database.
653
     *
654
     * @param array $params      Course details (see code for details).
655
     * @param int   $accessUrlId Optional.
656
     *
657
     * @return int Created course ID
658
     *
659
     * @todo use an array called $params instead of lots of params
660
     * @assert (null) === false
661
     */
662
    public static function register_course($params, $accessUrlId = 1)
663
    {
664
        global $error_msg;
665
        $title = $params['title'];
666
        // Fix amp
667
        $title = str_replace('&amp;', '&', $title);
668
        $code = $params['code'];
669
        $visual_code = $params['visual_code'];
670
        $directory = $params['directory'];
671
        $tutor_name = isset($params['tutor_name']) ? $params['tutor_name'] : null;
672
        $course_language = isset($params['course_language']) && !empty($params['course_language']) ? $params['course_language'] : api_get_setting(
673
            'platformLanguage'
674
        );
675
        $department_name = isset($params['department_name']) ? $params['department_name'] : null;
676
        $department_url = isset($params['department_url']) ? $params['department_url'] : null;
677
        $disk_quota = isset($params['disk_quota']) ? $params['disk_quota'] : null;
678
679
        if (!isset($params['visibility'])) {
680
            $default_course_visibility = api_get_setting(
681
                'courses_default_creation_visibility'
682
            );
683
            if (isset($default_course_visibility)) {
684
                $visibility = $default_course_visibility;
685
            } else {
686
                $visibility = COURSE_VISIBILITY_OPEN_PLATFORM;
687
            }
688
        } else {
689
            $visibility = $params['visibility'];
690
        }
691
692
        $subscribe = isset($params['subscribe']) ? (int) $params['subscribe'] : COURSE_VISIBILITY_OPEN_PLATFORM == $visibility ? 1 : 0;
693
        $unsubscribe = isset($params['unsubscribe']) ? (int) $params['unsubscribe'] : 0;
694
        $expiration_date = isset($params['expiration_date']) ? $params['expiration_date'] : null;
695
        $teachers = isset($params['teachers']) ? $params['teachers'] : null;
696
        $categories = isset($params['course_categories']) ? $params['course_categories'] : null;
697
        $ok_to_register_course = true;
698
699
        // Check whether all the needed parameters are present.
700
        if (empty($code)) {
701
            $error_msg[] = 'courseSysCode is missing';
702
            $ok_to_register_course = false;
703
        }
704
        if (empty($visual_code)) {
705
            $error_msg[] = 'courseScreenCode is missing';
706
            $ok_to_register_course = false;
707
        }
708
        if (empty($directory)) {
709
            $error_msg[] = 'courseRepository is missing';
710
            $ok_to_register_course = false;
711
        }
712
713
        if (empty($title)) {
714
            $error_msg[] = 'title is missing';
715
            $ok_to_register_course = false;
716
        }
717
718
        if (empty($expiration_date)) {
719
            $expiration_date = api_get_utc_datetime(
720
                time() + self::FIRST_EXPIRATION_DATE
721
            );
722
        } else {
723
            $expiration_date = api_get_utc_datetime($expiration_date);
724
        }
725
726
        if ($visibility < 0 || $visibility > 4) {
727
            $error_msg[] = 'visibility is invalid';
728
            $ok_to_register_course = false;
729
        }
730
731
        if (empty($disk_quota)) {
732
            $disk_quota = api_get_setting('default_document_quotum');
733
        }
734
735
        if (false === stripos($department_url, 'http://') && false === stripos(
736
                $department_url,
737
                'https://'
738
            )
739
        ) {
740
            $department_url = 'http://'.$department_url;
741
        }
742
743
        // just in case
744
        if ('http://' === $department_url) {
745
            $department_url = '';
746
        }
747
        $course_id = 0;
748
749
        $userId = empty($params['user_id']) ? api_get_user_id() : (int) $params['user_id'];
750
        $user = api_get_user_entity($userId);
751
        if (null === $user) {
752
            error_log(sprintf('user_id "%s" is invalid', $userId));
753
754
            return 0;
755
        }
756
757
        if ($ok_to_register_course) {
758
            $repo = Container::getCourseRepository();
759
            $categoryRepo = Container::getCourseCategoryRepository();
760
761
            $course = new Course();
762
            $course
763
                ->setCode($code)
764
                ->setDirectory($directory)
765
                ->setCourseLanguage($course_language)
766
                ->setTitle($title)
767
                ->setDescription(get_lang('Course Description'))
768
                ->setVisibility($visibility)
769
                ->setShowScore(1)
770
                ->setDiskQuota($disk_quota)
771
                ->setCreationDate(new \DateTime())
772
                ->setExpirationDate(new \DateTime($expiration_date))
773
                ->setDepartmentName($department_name)
774
                ->setDepartmentUrl($department_url)
775
                ->setSubscribe($subscribe)
776
                ->setUnsubscribe($unsubscribe)
777
                ->setVisualCode($visual_code)
778
            ;
779
780
            if (!empty($categories)) {
781
                if (!is_array($categories)) {
782
                    $categories = [$categories];
783
                }
784
785
                foreach ($categories as $key) {
786
                    if (empty($key)) {
787
                        continue;
788
                    }
789
790
                    $category = $categoryRepo->find($key);
791
792
                    $course->addCategory($category);
793
                }
794
            }
795
796
            $repo->getEntityManager()->persist($course);
797
            $repo->getEntityManager()->flush();
798
799
            $course_id = $course->getId();
800
            if ($course_id) {
801
                $sort = api_max_sort_value('0', api_get_user_id());
802
                // Default true
803
                $addTeacher = isset($params['add_user_as_teacher']) ? $params['add_user_as_teacher'] : true;
804
                if ($addTeacher) {
805
                    $iCourseSort = CourseManager::userCourseSort($userId, $code);
806
                    $courseRelTutor = (new CourseRelUser())
807
                        ->setCourse($course)
808
                        ->setUser($user)
809
                        ->setStatus(true)
810
                        ->setTutor(true)
811
                        ->setSort($iCourseSort)
812
                        ->setRelationType(0)
813
                        ->setUserCourseCat(0)
814
                    ;
815
                    Database::getManager()->persist($courseRelTutor);
816
                }
817
818
                if (!empty($teachers)) {
819
                    $sort = $user->getMaxSortValue();
820
                    if (!is_array($teachers)) {
821
                        $teachers = [$teachers];
822
                    }
823
                    foreach ($teachers as $key) {
824
                        // Just in case.
825
                        if ($key == $userId) {
826
                            continue;
827
                        }
828
                        if (empty($key)) {
829
                            continue;
830
                        }
831
                        $teacher = api_get_user_entity($key);
832
                        if (is_null($teacher)) {
833
                            continue;
834
                        }
835
                        $courseRelTeacher = (new CourseRelUser())
836
                            ->setCourse($course)
837
                            ->setUser($teacher)
838
                            ->setStatus(true)
839
                            ->setTutor(false)
840
                            ->setSort($sort + 1)
841
                            ->setRelationType(0)
842
                            ->setUserCourseCat(0)
843
                        ;
844
                        Database::getManager()->persist($courseRelTeacher);
845
                    }
846
                }
847
848
                // Adding the course to an URL.
849
                //UrlManager::add_course_to_url($course_id, $accessUrlId);
850
851
                // Add event to the system log.
852
                Event::addEvent(
853
                    LOG_COURSE_CREATE,
854
                    LOG_COURSE_CODE,
855
                    $code,
856
                    api_get_utc_datetime(),
857
                    $userId,
858
                    $course_id
859
                );
860
861
                $send_mail_to_admin = api_get_setting('send_email_to_admin_when_create_course');
862
863
                // @todo Improve code to send to all current portal administrators.
864
                if ('true' === $send_mail_to_admin) {
865
                    $siteName = api_get_setting('siteName');
866
                    $recipient_email = api_get_setting('emailAdministrator');
867
                    $recipient_name = api_get_person_name(
868
                        api_get_setting('administratorName'),
869
                        api_get_setting('administratorSurname')
870
                    );
871
                    $iname = api_get_setting('Institution');
872
                    $subject = get_lang(
873
                            'NewCourseCreatedIn'
874
                        ).' '.$siteName.' - '.$iname;
875
                    $message = get_lang(
876
                            'Dear'
877
                        ).' '.$recipient_name.",\n\n".get_lang(
878
                            'MessageOfNewCourseToAdmin'
879
                        ).' '.$siteName.' - '.$iname."\n";
880
                    $message .= get_lang('Course name').' '.$title."\n";
881
882
                    if ($course->getCategories()->count() > 0) {
883
                        foreach ($course->getCategories() as $category) {
884
                            $message .= get_lang('Category').': '.$category->getCode()."\n";
885
                        }
886
                    }
887
                    $message .= get_lang('Coach').' '.$tutor_name."\n";
888
                    $message .= get_lang('Language').' '.$course_language;
889
890
                    $additionalParameters = [
891
                        'smsType' => SmsPlugin::NEW_COURSE_BEEN_CREATED,
892
                        'userId' => $userId,
893
                        'courseName' => $title,
894
                        'creatorUsername' => $user->getUsername(),
895
                    ];
896
897
                    api_mail_html(
898
                        $recipient_name,
899
                        $recipient_email,
900
                        $subject,
901
                        $message,
902
                        $siteName,
903
                        $recipient_email,
904
                        null,
905
                        null,
906
                        null,
907
                        $additionalParameters
908
                    );
909
                }
910
            }
911
        }
912
913
        return $course_id;
914
    }
915
916
    /**
917
     * Generate a new id for c_tool table.
918
     *
919
     * @param int $courseId The course id
920
     *
921
     * @return int the new id
922
     */
923
    public static function generateToolId($courseId)
924
    {
925
        $newIdResultData = Database::select(
926
            'id + 1 AS new_id',
927
            Database::get_course_table(TABLE_TOOL_LIST),
928
            [
929
                'where' => ['c_id = ?' => intval($courseId)],
930
                'order' => 'id',
931
                'limit' => 1,
932
            ],
933
            'first'
934
        );
935
936
        if (false === $newIdResultData) {
937
            return 1;
938
        }
939
940
        return $newIdResultData['new_id'] > 0 ? $newIdResultData['new_id'] : 1;
941
    }
942
}
943