Total Complexity | 549 |
Total Lines | 3912 |
Duplicated Lines | 0 % |
Changes | 7 | ||
Bugs | 1 | Features | 0 |
Complex classes like CourseRestorer often do a lot of different things. To break such a class down, we need to identify a cohesive component within that class. A common approach to find such a component is to look for fields/methods that share the same prefixes, or suffixes.
Once you have determined the fields that belong together, you can apply the Extract Class refactoring. If the component makes sense as a sub-class, Extract Subclass is also a candidate, and is often faster.
While breaking up the class, it is a good idea to analyze how other classes use CourseRestorer, and based on these observations, apply Extract Interface, too.
1 | <?php |
||
29 | class CourseRestorer |
||
30 | { |
||
31 | /** |
||
32 | * The course-object. |
||
33 | */ |
||
34 | public $course; |
||
35 | public $destination_course_info; |
||
36 | |||
37 | /** |
||
38 | * What to do with files with same name (FILE_SKIP, FILE_RENAME or |
||
39 | * FILE_OVERWRITE). |
||
40 | */ |
||
41 | public $file_option; |
||
42 | public $set_tools_invisible_by_default; |
||
43 | public $skip_content; |
||
44 | public $tools_to_restore = [ |
||
45 | 'documents', // first restore documents |
||
46 | 'announcements', |
||
47 | 'attendance', |
||
48 | 'course_descriptions', |
||
49 | 'events', |
||
50 | 'forum_category', |
||
51 | 'forums', |
||
52 | // 'forum_topics', |
||
53 | 'glossary', |
||
54 | 'quizzes', |
||
55 | 'test_category', |
||
56 | 'links', |
||
57 | 'works', |
||
58 | 'xapi_tool', |
||
59 | 'surveys', |
||
60 | 'learnpath_category', |
||
61 | 'learnpaths', |
||
62 | //'scorm_documents', ?? |
||
63 | 'tool_intro', |
||
64 | 'thematic', |
||
65 | 'wiki', |
||
66 | 'gradebook', |
||
67 | 'assets', |
||
68 | ]; |
||
69 | |||
70 | /** Setting per tool */ |
||
71 | public $tool_copy_settings = []; |
||
72 | public $isXapiEnabled = false; |
||
73 | |||
74 | /** |
||
75 | * If true adds the text "copy" in the title of an item (only for LPs right now). |
||
76 | */ |
||
77 | public $add_text_in_items = false; |
||
78 | public $destination_course_id; |
||
79 | |||
80 | /** |
||
81 | * CourseRestorer constructor. |
||
82 | * |
||
83 | * @param Course $course |
||
84 | */ |
||
85 | public function __construct($course) |
||
86 | { |
||
87 | $this->course = $course; |
||
88 | $courseInfo = api_get_course_info($this->course->code); |
||
89 | $this->course_origin_id = null; |
||
90 | if (!empty($courseInfo)) { |
||
91 | $this->course_origin_id = $courseInfo['real_id']; |
||
92 | } |
||
93 | $this->file_option = FILE_RENAME; |
||
94 | $this->set_tools_invisible_by_default = false; |
||
95 | $this->skip_content = []; |
||
96 | |||
97 | $forceImport = api_get_configuration_value('allow_import_scorm_package_in_course_builder'); |
||
98 | if ($forceImport) { |
||
99 | $this->tools_to_restore[] = 'scorm_documents'; |
||
100 | } |
||
101 | } |
||
102 | |||
103 | /** |
||
104 | * Set the file-option. |
||
105 | * |
||
106 | * @param int $option (optional) What to do with files with same name |
||
107 | * FILE_SKIP, FILE_RENAME or FILE_OVERWRITE |
||
108 | */ |
||
109 | public function set_file_option($option = FILE_OVERWRITE) |
||
110 | { |
||
111 | $this->file_option = $option; |
||
112 | } |
||
113 | |||
114 | /** |
||
115 | * @param bool $status |
||
116 | */ |
||
117 | public function set_add_text_in_items($status) |
||
118 | { |
||
119 | $this->add_text_in_items = $status; |
||
120 | } |
||
121 | |||
122 | /** |
||
123 | * @param array $array |
||
124 | */ |
||
125 | public function set_tool_copy_settings($array) |
||
126 | { |
||
127 | $this->tool_copy_settings = $array; |
||
128 | } |
||
129 | |||
130 | /** |
||
131 | * Restore a course. |
||
132 | * |
||
133 | * @param string $destination_course_code code of the Chamilo-course in |
||
134 | * @param int $session_id |
||
135 | * @param bool $update_course_settings Course settings are going to be restore? |
||
136 | * @param bool $respect_base_content |
||
137 | * |
||
138 | * @return false|null |
||
139 | */ |
||
140 | public function restore( |
||
141 | $destination_course_code = '', |
||
142 | $session_id = 0, |
||
143 | $update_course_settings = false, |
||
144 | $respect_base_content = false |
||
145 | ) { |
||
146 | if ($destination_course_code == '') { |
||
147 | $course_info = api_get_course_info(); |
||
148 | $this->destination_course_info = $course_info; |
||
149 | $this->course->destination_path = $course_info['path']; |
||
150 | } else { |
||
151 | $course_info = api_get_course_info($destination_course_code); |
||
152 | $this->destination_course_info = $course_info; |
||
153 | $this->course->destination_path = $course_info['path']; |
||
154 | } |
||
155 | $this->destination_course_id = $course_info['real_id']; |
||
156 | // Getting first teacher (for the forums) |
||
157 | $teacher_list = CourseManager::get_teacher_list_from_course_code($course_info['code']); |
||
158 | $this->first_teacher_id = api_get_user_id(); |
||
159 | $this->isXapiEnabled = \XApiPlugin::create()->isEnabled(); |
||
160 | |||
161 | if (!empty($teacher_list)) { |
||
162 | foreach ($teacher_list as $teacher) { |
||
163 | $this->first_teacher_id = $teacher['user_id']; |
||
164 | break; |
||
165 | } |
||
166 | } |
||
167 | |||
168 | if (empty($this->course)) { |
||
169 | return false; |
||
170 | } |
||
171 | |||
172 | // Source platform encoding - reading/detection |
||
173 | // The correspondent data field has been added as of version 1.8.6.1 |
||
174 | if (empty($this->course->encoding)) { |
||
175 | // The archive has been created by a system which is prior to 1.8.6.1 version. |
||
176 | // In this case we have to detect the encoding. |
||
177 | $sample_text = $this->course->get_sample_text()."\n"; |
||
178 | // Let us exclude ASCII lines, probably they are English texts. |
||
179 | $sample_text = explode("\n", $sample_text); |
||
180 | foreach ($sample_text as $key => &$line) { |
||
181 | if (api_is_valid_ascii($line)) { |
||
182 | unset($sample_text[$key]); |
||
183 | } |
||
184 | } |
||
185 | $sample_text = implode("\n", $sample_text); |
||
186 | $this->course->encoding = api_detect_encoding( |
||
187 | $sample_text, |
||
188 | $course_info['language'] |
||
189 | ); |
||
190 | } |
||
191 | |||
192 | // Encoding conversion of the course, if it is needed. |
||
193 | $this->course->to_system_encoding(); |
||
194 | |||
195 | foreach ($this->tools_to_restore as $tool) { |
||
196 | if ('xapi_tool' == $tool && !$this->isXapiEnabled) { |
||
197 | continue; |
||
198 | } |
||
199 | $function_build = 'restore_'.$tool; |
||
200 | $this->$function_build( |
||
201 | $session_id, |
||
202 | $respect_base_content, |
||
203 | $destination_course_code |
||
204 | ); |
||
205 | } |
||
206 | |||
207 | if ($update_course_settings) { |
||
208 | $this->restore_course_settings($destination_course_code); |
||
209 | } |
||
210 | |||
211 | // Restore the item properties |
||
212 | $table = Database::get_course_table(TABLE_ITEM_PROPERTY); |
||
213 | foreach ($this->course->resources as $type => $resources) { |
||
214 | if (is_array($resources)) { |
||
215 | foreach ($resources as $id => $resource) { |
||
216 | if (isset($resource->item_properties)) { |
||
217 | foreach ($resource->item_properties as $property) { |
||
218 | // First check if there isn't already a record for this resource |
||
219 | $sql = "SELECT * FROM $table |
||
220 | WHERE |
||
221 | c_id = ".$this->destination_course_id." AND |
||
222 | tool = '".$property['tool']."' AND |
||
223 | ref = '".$resource->destination_id."'"; |
||
224 | |||
225 | $params = []; |
||
226 | if (!empty($session_id)) { |
||
227 | $params['session_id'] = (int) $session_id; |
||
228 | } |
||
229 | |||
230 | $res = Database::query($sql); |
||
231 | if (Database::num_rows($res) == 0) { |
||
232 | /* The to_group_id and to_user_id are set to default |
||
233 | values as users/groups possibly not exist in |
||
234 | the target course*/ |
||
235 | |||
236 | $params['c_id'] = $this->destination_course_id; |
||
237 | $params['tool'] = self::DBUTF8($property['tool']); |
||
238 | $params['insert_user_id'] = $this->checkUserId($property['insert_user_id']) ?: null; |
||
239 | $params['insert_date'] = self::DBUTF8($property['insert_date']); |
||
240 | $params['lastedit_date'] = self::DBUTF8($property['lastedit_date']); |
||
241 | $params['ref'] = $resource->destination_id; |
||
242 | $params['lastedit_type'] = self::DBUTF8($property['lastedit_type']); |
||
243 | $params['lastedit_user_id'] = $this->checkUserId($property['lastedit_user_id']); |
||
244 | $params['visibility'] = self::DBUTF8($property['visibility']); |
||
245 | $params['start_visible'] = self::DBUTF8($property['start_visible']); |
||
246 | $params['end_visible'] = self::DBUTF8($property['end_visible']); |
||
247 | $params['to_user_id'] = $this->checkUserId($property['to_user_id']) ?: null; |
||
248 | |||
249 | $id = Database::insert($table, $params); |
||
250 | if ($id) { |
||
251 | $sql = "UPDATE $table SET id = iid WHERE iid = $id"; |
||
252 | Database::query($sql); |
||
253 | } |
||
254 | } |
||
255 | } |
||
256 | } |
||
257 | } |
||
258 | } |
||
259 | } |
||
260 | } |
||
261 | |||
262 | /** |
||
263 | * Restore only harmless course settings: |
||
264 | * course_language, visibility, department_name,department_url, |
||
265 | * subscribe, unsubscribe ,category_code. |
||
266 | * |
||
267 | * @param string $destination_course_code |
||
268 | */ |
||
269 | public function restore_course_settings($destination_course_code) |
||
270 | { |
||
271 | $origin_course_info = api_get_course_info($destination_course_code); |
||
272 | $course_info = $this->course->info; |
||
273 | $params['course_language'] = $course_info['language']; |
||
274 | $params['visibility'] = $course_info['visibility']; |
||
275 | $params['department_name'] = $course_info['department_name']; |
||
276 | $params['department_url'] = $course_info['department_url']; |
||
277 | $params['category_code'] = $course_info['categoryCode']; |
||
278 | $params['subscribe'] = $course_info['subscribe_allowed']; |
||
279 | $params['unsubscribe'] = $course_info['unsubscribe']; |
||
280 | CourseManager::update_attributes($origin_course_info['real_id'], $params); |
||
281 | } |
||
282 | |||
283 | /** |
||
284 | * Restore documents. |
||
285 | * |
||
286 | * @param int $session_id |
||
287 | * @param bool $respect_base_content |
||
288 | * @param string $destination_course_code |
||
289 | */ |
||
290 | public function restore_documents( |
||
291 | $session_id = 0, |
||
292 | $respect_base_content = false, |
||
293 | $destination_course_code = '' |
||
294 | ) { |
||
295 | $course_info = api_get_course_info($destination_course_code); |
||
296 | |||
297 | if (!$this->course->has_resources(RESOURCE_DOCUMENT)) { |
||
298 | return; |
||
299 | } |
||
300 | |||
301 | $webEditorCss = api_get_path(WEB_CSS_PATH).'editor.css'; |
||
302 | $table = Database::get_course_table(TABLE_DOCUMENT); |
||
303 | $resources = $this->course->resources; |
||
304 | $path = api_get_path(SYS_COURSE_PATH).$this->course->destination_path.'/'; |
||
305 | $originalFolderNameList = []; |
||
306 | foreach ($resources[RESOURCE_DOCUMENT] as $id => $document) { |
||
307 | $my_session_id = empty($document->item_properties[0]['session_id']) ? 0 : $session_id; |
||
308 | |||
309 | if (false === $respect_base_content && $session_id) { |
||
310 | if (empty($my_session_id)) { |
||
311 | $my_session_id = $session_id; |
||
312 | } |
||
313 | } |
||
314 | |||
315 | if ($document->file_type == FOLDER) { |
||
316 | $visibility = isset($document->item_properties[0]['visibility']) ? $document->item_properties[0]['visibility'] : ''; |
||
317 | $new = substr($document->path, 8); |
||
318 | $folderList = explode('/', $new); |
||
319 | $tempFolder = ''; |
||
320 | |||
321 | // Check if the parent path exists. |
||
322 | foreach ($folderList as $folder) { |
||
323 | $folderToCreate = $tempFolder.$folder; |
||
324 | $sysFolderPath = $path.'document'.$folderToCreate; |
||
325 | $tempFolder .= $folder.'/'; |
||
326 | |||
327 | if (empty($folderToCreate)) { |
||
328 | continue; |
||
329 | } |
||
330 | $title = $document->title; |
||
331 | $originalFolderNameList[basename($document->path)] = $document->title; |
||
332 | if (empty($title)) { |
||
333 | $title = basename($sysFolderPath); |
||
334 | } |
||
335 | //error_log($title); error_log($sysFolderPath); |
||
336 | // File doesn't exist in file system. |
||
337 | if (!is_dir($sysFolderPath)) { |
||
338 | /*error_log('Creating directory'); |
||
339 | error_log("Creating $folderToCreate");*/ |
||
340 | // Creating directory |
||
341 | create_unexisting_directory( |
||
342 | $course_info, |
||
343 | api_get_user_id(), |
||
344 | $my_session_id, |
||
345 | 0, |
||
346 | 0, |
||
347 | $path.'document', |
||
348 | $folderToCreate, |
||
349 | $title, |
||
350 | $visibility |
||
351 | ); |
||
352 | continue; |
||
353 | } |
||
354 | |||
355 | // File exist in file system. |
||
356 | $documentData = DocumentManager::get_document_id( |
||
357 | $course_info, |
||
358 | $folderToCreate, |
||
359 | $session_id |
||
360 | ); |
||
361 | |||
362 | //error_log("session_id $session_id"); |
||
363 | if (empty($documentData)) { |
||
364 | if (!is_dir($sysFolderPath)) { |
||
365 | //error_log('$documentData empty'); |
||
366 | //error_log('$folderToCreate '.$folderToCreate); |
||
367 | /* This means the folder exists in the |
||
368 | filesystem but not in the DB, trying to fix it */ |
||
369 | add_document( |
||
370 | $course_info, |
||
371 | $folderToCreate, |
||
372 | 'folder', |
||
373 | 0, |
||
374 | $title, |
||
375 | null, |
||
376 | null, |
||
377 | false, |
||
378 | null, |
||
379 | $session_id, |
||
380 | 0, |
||
381 | false |
||
382 | ); |
||
383 | } |
||
384 | } else { |
||
385 | $insertUserId = isset($document->item_properties[0]['insert_user_id']) ? $document->item_properties[0]['insert_user_id'] : api_get_user_id(); |
||
386 | $insertUserId = $this->checkUserId($insertUserId); |
||
387 | // Check if user exists in platform |
||
388 | $toUserId = isset($document->item_properties[0]['to_user_id']) ? $document->item_properties[0]['to_user_id'] : null; |
||
389 | $toUserId = $this->checkUserId($toUserId, true); |
||
390 | $groupId = isset($document->item_properties[0]['to_group_id']) ? $document->item_properties[0]['to_group_id'] : null; |
||
391 | $groupInfo = $this->checkGroupId($groupId); |
||
392 | //error_log(" if folder exists then just refresh it"); |
||
393 | // if folder exists then just refresh it |
||
394 | api_item_property_update( |
||
395 | $course_info, |
||
396 | TOOL_DOCUMENT, |
||
397 | $documentData, |
||
398 | 'FolderUpdated', |
||
399 | $insertUserId, |
||
400 | $groupInfo, |
||
401 | $toUserId, |
||
402 | null, |
||
403 | null, |
||
404 | $my_session_id |
||
405 | ); |
||
406 | } |
||
407 | } |
||
408 | } elseif ($document->file_type == DOCUMENT) { |
||
409 | // Checking if folder exists in the database otherwise we created it |
||
410 | $dir_to_create = dirname($document->path); |
||
411 | $originalFolderNameList[basename($document->path)] = $document->title; |
||
412 | if (!empty($dir_to_create) && $dir_to_create != 'document' && $dir_to_create != '/') { |
||
413 | // it creates folder images if it doesn't exist , used for hotspot pictures. |
||
414 | if (false !== strpos($document->path, '/images/') && !is_dir(dirname($path.$document->path))) { |
||
415 | $perm = api_get_permissions_for_new_directories(); |
||
416 | mkdir(dirname($path.$document->path), $perm, true); |
||
417 | } |
||
418 | if (is_dir($path.dirname($document->path))) { |
||
419 | $sql = "SELECT id FROM $table |
||
420 | WHERE |
||
421 | c_id = ".$this->destination_course_id." AND |
||
422 | path = '/".self::DBUTF8escapestring(substr(dirname($document->path), 9))."'"; |
||
423 | $res = Database::query($sql); |
||
424 | |||
425 | if (Database::num_rows($res) == 0) { |
||
426 | $new = '/'.substr(dirname($document->path), 9); |
||
427 | // It adds the folder name as title |
||
428 | $title = str_replace('/', '', $new); |
||
429 | |||
430 | // This code fixes the possibility for a file without a directory entry to be |
||
431 | $document_id = add_document( |
||
432 | $course_info, |
||
433 | $new, |
||
434 | 'folder', |
||
435 | 0, |
||
436 | $title, |
||
437 | null, |
||
438 | null, |
||
439 | false, |
||
440 | 0, |
||
441 | 0, |
||
442 | 0, |
||
443 | false |
||
444 | ); |
||
445 | |||
446 | $itemProperty = isset($document->item_properties[0]) ? $document->item_properties[0] : ''; |
||
447 | $insertUserId = isset($itemProperty['insert_user_id']) ? $itemProperty['insert_user_id'] : api_get_user_id(); |
||
448 | $toGroupId = isset($itemProperty['to_group_id']) ? $itemProperty['to_group_id'] : 0; |
||
449 | $toUserId = isset($itemProperty['to_user_id']) ? $itemProperty['to_user_id'] : null; |
||
450 | $groupInfo = $this->checkGroupId($toGroupId); |
||
451 | $insertUserId = $this->checkUserId($insertUserId); |
||
452 | $toUserId = $this->checkUserId($toUserId, true); |
||
453 | |||
454 | api_item_property_update( |
||
455 | $course_info, |
||
456 | TOOL_DOCUMENT, |
||
457 | $document_id, |
||
458 | 'FolderCreated', |
||
459 | $insertUserId, |
||
460 | $groupInfo, |
||
461 | $toUserId, |
||
462 | null, |
||
463 | null, |
||
464 | $my_session_id |
||
465 | ); |
||
466 | } |
||
467 | } |
||
468 | } |
||
469 | |||
470 | //error_log(print_r($originalFolderNameList, 1)); |
||
471 | if (file_exists($path.$document->path)) { |
||
472 | switch ($this->file_option) { |
||
473 | case FILE_OVERWRITE: |
||
474 | $origin_path = $this->course->backup_path.'/'.$document->path; |
||
475 | if (file_exists($origin_path)) { |
||
476 | copy($origin_path, $path.$document->path); |
||
477 | $this->fixEditorHtmlContent($path.$document->path, $webEditorCss); |
||
478 | $sql = "SELECT id FROM $table |
||
479 | WHERE |
||
480 | c_id = ".$this->destination_course_id." AND |
||
481 | path = '/".self::DBUTF8escapestring(substr($document->path, 9))."'"; |
||
482 | |||
483 | $res = Database::query($sql); |
||
484 | $count = Database::num_rows($res); |
||
485 | |||
486 | if ($count == 0) { |
||
487 | $params = [ |
||
488 | 'path' => "/".self::DBUTF8(substr($document->path, 9)), |
||
489 | 'c_id' => $this->destination_course_id, |
||
490 | 'comment' => self::DBUTF8($document->comment), |
||
491 | 'title' => self::DBUTF8($document->title), |
||
492 | 'filetype' => self::DBUTF8($document->file_type), |
||
493 | 'size' => self::DBUTF8($document->size), |
||
494 | 'session_id' => $my_session_id, |
||
495 | 'readonly' => 0, |
||
496 | ]; |
||
497 | |||
498 | $document_id = Database::insert($table, $params); |
||
499 | |||
500 | if ($document_id) { |
||
501 | $sql = "UPDATE $table SET id = iid WHERE iid = $document_id"; |
||
502 | Database::query($sql); |
||
503 | } |
||
504 | $this->course->resources[RESOURCE_DOCUMENT][$id]->destination_id = $document_id; |
||
505 | |||
506 | $itemProperty = isset($document->item_properties[0]) ? $document->item_properties[0] : ''; |
||
507 | $insertUserId = isset($itemProperty['insert_user_id']) ? $itemProperty['insert_user_id'] : api_get_user_id(); |
||
508 | $toGroupId = isset($itemProperty['to_group_id']) ? $itemProperty['to_group_id'] : 0; |
||
509 | $toUserId = isset($itemProperty['to_user_id']) ? $itemProperty['to_user_id'] : null; |
||
510 | |||
511 | $insertUserId = $this->checkUserId($insertUserId); |
||
512 | $toUserId = $this->checkUserId($toUserId, true); |
||
513 | $groupInfo = $this->checkGroupId($toGroupId); |
||
514 | |||
515 | api_item_property_update( |
||
516 | $course_info, |
||
517 | TOOL_DOCUMENT, |
||
518 | $document_id, |
||
519 | 'DocumentAdded', |
||
520 | $insertUserId, |
||
521 | $groupInfo, |
||
522 | $toUserId, |
||
523 | null, |
||
524 | null, |
||
525 | $my_session_id |
||
526 | ); |
||
527 | } else { |
||
528 | $obj = Database::fetch_object($res); |
||
529 | $document_id = $obj->id; |
||
530 | $params = [ |
||
531 | 'path' => "/".self::DBUTF8(substr($document->path, 9)), |
||
532 | 'c_id' => $this->destination_course_id, |
||
533 | 'comment' => self::DBUTF8($document->comment), |
||
534 | 'title' => self::DBUTF8($document->title), |
||
535 | 'filetype' => self::DBUTF8($document->file_type), |
||
536 | 'size' => self::DBUTF8($document->size), |
||
537 | 'session_id' => $my_session_id, |
||
538 | ]; |
||
539 | |||
540 | Database::update( |
||
541 | $table, |
||
542 | $params, |
||
543 | [ |
||
544 | 'c_id = ? AND path = ?' => [ |
||
545 | $this->destination_course_id, |
||
546 | "/".self::DBUTF8escapestring(substr($document->path, 9)), |
||
547 | ], |
||
548 | ] |
||
549 | ); |
||
550 | |||
551 | $this->course->resources[RESOURCE_DOCUMENT][$id]->destination_id = $obj->id; |
||
552 | |||
553 | $itemProperty = isset($document->item_properties[0]) ? $document->item_properties[0] : ''; |
||
554 | $insertUserId = isset($itemProperty['insert_user_id']) ? $itemProperty['insert_user_id'] : api_get_user_id(); |
||
555 | $toGroupId = isset($itemProperty['to_group_id']) ? $itemProperty['to_group_id'] : 0; |
||
556 | $toUserId = isset($itemProperty['to_user_id']) ? $itemProperty['to_user_id'] : null; |
||
557 | |||
558 | $insertUserId = $this->checkUserId($insertUserId); |
||
559 | $toUserId = $this->checkUserId($toUserId, true); |
||
560 | $groupInfo = $this->checkGroupId($toGroupId); |
||
561 | |||
562 | api_item_property_update( |
||
563 | $course_info, |
||
564 | TOOL_DOCUMENT, |
||
565 | $obj->id, |
||
566 | 'default', |
||
567 | $insertUserId, |
||
568 | $groupInfo, |
||
569 | $toUserId, |
||
570 | null, |
||
571 | null, |
||
572 | $my_session_id |
||
573 | ); |
||
574 | } |
||
575 | |||
576 | // Replace old course code with the new destination code |
||
577 | $file_info = pathinfo($path.$document->path); |
||
578 | |||
579 | if (isset($file_info['extension']) && in_array($file_info['extension'], ['html', 'htm'])) { |
||
580 | $content = file_get_contents($path.$document->path); |
||
581 | if (UTF8_CONVERT) { |
||
582 | $content = utf8_encode($content); |
||
583 | } |
||
584 | $content = DocumentManager::replaceUrlWithNewCourseCode( |
||
585 | $content, |
||
586 | $this->course->code, |
||
587 | $this->course->destination_path, |
||
588 | $this->course->backup_path, |
||
589 | $this->course->info['path'] |
||
590 | ); |
||
591 | file_put_contents($path.$document->path, $content); |
||
592 | } |
||
593 | |||
594 | $params = [ |
||
595 | 'comment' => self::DBUTF8($document->comment), |
||
596 | 'title' => self::DBUTF8($document->title), |
||
597 | 'size' => self::DBUTF8($document->size), |
||
598 | ]; |
||
599 | Database::update( |
||
600 | $table, |
||
601 | $params, |
||
602 | [ |
||
603 | 'c_id = ? AND id = ?' => [ |
||
604 | $this->destination_course_id, |
||
605 | $document_id, |
||
606 | ], |
||
607 | ] |
||
608 | ); |
||
609 | } |
||
610 | break; |
||
611 | case FILE_SKIP: |
||
612 | $sql = "SELECT id FROM $table |
||
613 | WHERE |
||
614 | c_id = ".$this->destination_course_id." AND |
||
615 | path='/".self::DBUTF8escapestring(substr($document->path, 9))."'"; |
||
616 | $res = Database::query($sql); |
||
617 | $obj = Database::fetch_object($res); |
||
618 | $this->course->resources[RESOURCE_DOCUMENT][$id]->destination_id = $obj->id; |
||
619 | break; |
||
620 | case FILE_RENAME: |
||
621 | //error_log("Rename: ".$path.$document->path); |
||
622 | $i = 1; |
||
623 | $ext = explode('.', basename($document->path)); |
||
624 | if (count($ext) > 1) { |
||
625 | $ext = array_pop($ext); |
||
626 | $file_name_no_ext = substr($document->path, 0, -(strlen($ext) + 1)); |
||
627 | $ext = '.'.$ext; |
||
628 | } else { |
||
629 | $ext = ''; |
||
630 | $file_name_no_ext = $document->path; |
||
631 | } |
||
632 | $new_file_name = $file_name_no_ext.'_'.$i.$ext; |
||
633 | $file_exists = file_exists($path.$new_file_name); |
||
634 | while ($file_exists) { |
||
635 | $i++; |
||
636 | $new_file_name = $file_name_no_ext.'_'.$i.$ext; |
||
637 | $file_exists = file_exists($path.$new_file_name); |
||
638 | } |
||
639 | |||
640 | if (!empty($session_id)) { |
||
641 | $originalPath = $document->path; |
||
642 | //error_log("document->path: ".$document->path); |
||
643 | $document_path = explode('/', $document->path, 3); |
||
644 | $course_path = $path; |
||
645 | $orig_base_folder = $document_path[1]; |
||
646 | $orig_base_path = $course_path.$document_path[0].'/'.$document_path[1]; |
||
647 | |||
648 | if (is_dir($orig_base_path)) { |
||
649 | $new_base_foldername = $orig_base_folder; |
||
650 | $new_base_path = $orig_base_path; |
||
651 | |||
652 | if (isset($_SESSION['orig_base_foldername']) && |
||
653 | $_SESSION['orig_base_foldername'] != $new_base_foldername |
||
654 | ) { |
||
655 | unset($_SESSION['new_base_foldername']); |
||
656 | unset($_SESSION['orig_base_foldername']); |
||
657 | unset($_SESSION['new_base_path']); |
||
658 | } |
||
659 | |||
660 | $folder_exists = file_exists($new_base_path); |
||
661 | if ($folder_exists) { |
||
662 | // e.g: carpeta1 in session |
||
663 | $_SESSION['orig_base_foldername'] = $new_base_foldername; |
||
664 | $x = 0; |
||
665 | while ($folder_exists) { |
||
666 | $x = $x + 1; |
||
667 | $new_base_foldername = $document_path[1].'_'.$x; |
||
668 | $new_base_path = $orig_base_path.'_'.$x; |
||
669 | if (isset($_SESSION['new_base_foldername']) && |
||
670 | $_SESSION['new_base_foldername'] == $new_base_foldername |
||
671 | ) { |
||
672 | break; |
||
673 | } |
||
674 | $folder_exists = file_exists($new_base_path); |
||
675 | } |
||
676 | $_SESSION['new_base_foldername'] = $new_base_foldername; |
||
677 | $_SESSION['new_base_path'] = $new_base_path; |
||
678 | } |
||
679 | |||
680 | if (isset($_SESSION['new_base_foldername']) && isset($_SESSION['new_base_path'])) { |
||
681 | $new_base_foldername = $_SESSION['new_base_foldername']; |
||
682 | $new_base_path = $_SESSION['new_base_path']; |
||
683 | } |
||
684 | |||
685 | $dest_document_path = $new_base_path.'/'.$document_path[2]; // e.g: "/var/www/wiener/courses/CURSO4/document/carpeta1_1/subcarpeta1/collaborative.png" |
||
686 | $basedir_dest_path = dirname($dest_document_path); // e.g: "/var/www/wiener/courses/CURSO4/document/carpeta1_1/subcarpeta1" |
||
687 | $base_path_document = $course_path.$document_path[0]; // e.g: "/var/www/wiener/courses/CURSO4/document" |
||
688 | $path_title = '/'.$new_base_foldername.'/'.$document_path[2]; |
||
689 | |||
690 | /*error_log("copy_folder_course_session"); |
||
691 | error_log("original: $orig_base_path"); |
||
692 | error_log($basedir_dest_path); |
||
693 | error_log($document->title);*/ |
||
694 | |||
695 | copy_folder_course_session( |
||
696 | $basedir_dest_path, |
||
697 | $base_path_document, |
||
698 | $session_id, |
||
699 | $course_info, |
||
700 | $document, |
||
701 | $this->course_origin_id, |
||
702 | $originalFolderNameList, |
||
703 | $originalPath |
||
704 | ); |
||
705 | |||
706 | if (file_exists($course_path.$document->path)) { |
||
707 | copy($course_path.$document->path, $dest_document_path); |
||
708 | } |
||
709 | |||
710 | // Replace old course code with the new destination code see BT#1985 |
||
711 | if (file_exists($dest_document_path)) { |
||
712 | $file_info = pathinfo($dest_document_path); |
||
713 | if (in_array($file_info['extension'], ['html', 'htm'])) { |
||
714 | $content = file_get_contents($dest_document_path); |
||
715 | if (UTF8_CONVERT) { |
||
716 | $content = utf8_encode($content); |
||
717 | } |
||
718 | $content = DocumentManager::replaceUrlWithNewCourseCode( |
||
719 | $content, |
||
720 | $this->course->code, |
||
721 | $this->course->destination_path, |
||
722 | $this->course->backup_path, |
||
723 | $this->course->info['path'] |
||
724 | ); |
||
725 | file_put_contents($dest_document_path, $content); |
||
726 | $this->fixEditorHtmlContent($dest_document_path, $webEditorCss); |
||
727 | } |
||
728 | } |
||
729 | |||
730 | $title = basename($path_title); |
||
731 | if (isset($originalFolderNameList[basename($path_title)])) { |
||
732 | $title = $originalFolderNameList[basename($path_title)]; |
||
733 | } |
||
734 | |||
735 | $params = [ |
||
736 | 'path' => self::DBUTF8($path_title), |
||
737 | 'c_id' => $this->destination_course_id, |
||
738 | 'comment' => self::DBUTF8($document->comment), |
||
739 | 'title' => self::DBUTF8($title), |
||
740 | 'filetype' => self::DBUTF8($document->file_type), |
||
741 | 'size' => self::DBUTF8($document->size), |
||
742 | 'session_id' => $my_session_id, |
||
743 | ]; |
||
744 | |||
745 | $document_id = Database::insert($table, $params); |
||
746 | |||
747 | if ($document_id) { |
||
748 | $sql = "UPDATE $table SET id = iid WHERE iid = $document_id"; |
||
749 | Database::query($sql); |
||
750 | |||
751 | $this->course->resources[RESOURCE_DOCUMENT][$id]->destination_id = $document_id; |
||
752 | |||
753 | $itemProperty = isset($document->item_properties[0]) ? $document->item_properties[0] : ''; |
||
754 | $insertUserId = isset($itemProperty['insert_user_id']) ? $itemProperty['insert_user_id'] : api_get_user_id(); |
||
755 | $toGroupId = isset($itemProperty['to_group_id']) ? $itemProperty['to_group_id'] : 0; |
||
756 | $toUserId = isset($itemProperty['to_user_id']) ? $itemProperty['to_user_id'] : null; |
||
757 | |||
758 | $insertUserId = $this->checkUserId($insertUserId); |
||
759 | $toUserId = $this->checkUserId($toUserId, true); |
||
760 | $groupInfo = $this->checkGroupId($toGroupId); |
||
761 | |||
762 | api_item_property_update( |
||
763 | $course_info, |
||
764 | TOOL_DOCUMENT, |
||
765 | $document_id, |
||
766 | 'DocumentAdded', |
||
767 | $insertUserId, |
||
768 | $groupInfo, |
||
769 | $toUserId, |
||
770 | null, |
||
771 | null, |
||
772 | $my_session_id |
||
773 | ); |
||
774 | } |
||
775 | } else { |
||
776 | if (file_exists($path.$document->path)) { |
||
777 | copy($path.$document->path, $path.$new_file_name); |
||
778 | } |
||
779 | // Replace old course code with the new destination code see BT#1985 |
||
780 | if (file_exists($path.$new_file_name)) { |
||
781 | $file_info = pathinfo($path.$new_file_name); |
||
782 | if (in_array($file_info['extension'], ['html', 'htm'])) { |
||
783 | $content = file_get_contents($path.$new_file_name); |
||
784 | if (UTF8_CONVERT) { |
||
785 | $content = utf8_encode($content); |
||
786 | } |
||
787 | $content = DocumentManager::replaceUrlWithNewCourseCode( |
||
788 | $content, |
||
789 | $this->course->code, |
||
790 | $this->course->destination_path, |
||
791 | $this->course->backup_path, |
||
792 | $this->course->info['path'] |
||
793 | ); |
||
794 | file_put_contents($path.$new_file_name, $content); |
||
795 | $this->fixEditorHtmlContent($path.$new_file_name, $webEditorCss); |
||
796 | } |
||
797 | } |
||
798 | |||
799 | $params = [ |
||
800 | 'path' => "/".self::DBUTF8escapestring(substr($new_file_name, 9)), |
||
801 | 'c_id' => $this->destination_course_id, |
||
802 | 'comment' => self::DBUTF8($document->comment), |
||
803 | 'title' => self::DBUTF8($document->title), |
||
804 | 'filetype' => self::DBUTF8($document->file_type), |
||
805 | 'size' => self::DBUTF8($document->size), |
||
806 | 'session_id' => $my_session_id, |
||
807 | ]; |
||
808 | |||
809 | $document_id = Database::insert($table, $params); |
||
810 | |||
811 | if ($document_id) { |
||
812 | $sql = "UPDATE $table SET id = iid WHERE iid = $document_id"; |
||
813 | Database::query($sql); |
||
814 | |||
815 | $this->course->resources[RESOURCE_DOCUMENT][$id]->destination_id = $document_id; |
||
816 | |||
817 | $itemProperty = isset($document->item_properties[0]) ? $document->item_properties[0] : ''; |
||
818 | $insertUserId = isset($itemProperty['insert_user_id']) ? $itemProperty['insert_user_id'] : api_get_user_id(); |
||
819 | $toGroupId = isset($itemProperty['to_group_id']) ? $itemProperty['to_group_id'] : 0; |
||
820 | $toUserId = isset($itemProperty['to_user_id']) ? $itemProperty['to_user_id'] : null; |
||
821 | |||
822 | $insertUserId = $this->checkUserId($insertUserId); |
||
823 | $toUserId = $this->checkUserId($toUserId, true); |
||
824 | $groupInfo = $this->checkGroupId($toGroupId); |
||
825 | |||
826 | api_item_property_update( |
||
827 | $course_info, |
||
828 | TOOL_DOCUMENT, |
||
829 | $document_id, |
||
830 | 'DocumentAdded', |
||
831 | $insertUserId, |
||
832 | $groupInfo, |
||
833 | $toUserId, |
||
834 | null, |
||
835 | null, |
||
836 | $my_session_id |
||
837 | ); |
||
838 | } |
||
839 | } |
||
840 | } else { |
||
841 | copy( |
||
842 | $this->course->backup_path.'/'.$document->path, |
||
843 | $path.$new_file_name |
||
844 | ); |
||
845 | |||
846 | // Replace old course code with the new destination code see BT#1985 |
||
847 | if (file_exists($path.$new_file_name)) { |
||
848 | $file_info = pathinfo($path.$new_file_name); |
||
849 | if (in_array($file_info['extension'], ['html', 'htm'])) { |
||
850 | $content = file_get_contents($path.$new_file_name); |
||
851 | if (UTF8_CONVERT) { |
||
852 | $content = utf8_encode($content); |
||
853 | } |
||
854 | $content = DocumentManager::replaceUrlWithNewCourseCode( |
||
855 | $content, |
||
856 | $this->course->code, |
||
857 | $this->course->destination_path, |
||
858 | $this->course->backup_path, |
||
859 | $this->course->info['path'] |
||
860 | ); |
||
861 | file_put_contents($path.$new_file_name, $content); |
||
862 | $this->fixEditorHtmlContent($path.$new_file_name, $webEditorCss); |
||
863 | } |
||
864 | } |
||
865 | |||
866 | $params = [ |
||
867 | 'c_id' => $this->destination_course_id, |
||
868 | 'path' => "/".self::DBUTF8escapestring(substr($new_file_name, 9)), |
||
869 | 'comment' => self::DBUTF8($document->comment), |
||
870 | 'title' => self::DBUTF8($document->title), |
||
871 | 'filetype' => self::DBUTF8($document->file_type), |
||
872 | 'size' => self::DBUTF8($document->size), |
||
873 | 'session_id' => $my_session_id, |
||
874 | ]; |
||
875 | |||
876 | $document_id = Database::insert($table, $params); |
||
877 | |||
878 | if ($document_id) { |
||
879 | $sql = "UPDATE $table SET id = iid WHERE iid = $document_id"; |
||
880 | Database::query($sql); |
||
881 | $this->course->resources[RESOURCE_DOCUMENT][$id]->destination_id = $document_id; |
||
882 | |||
883 | $itemProperty = isset($document->item_properties[0]) ? $document->item_properties[0] : ''; |
||
884 | $insertUserId = isset($itemProperty['insert_user_id']) ? $itemProperty['insert_user_id'] : api_get_user_id(); |
||
885 | $toGroupId = isset($itemProperty['to_group_id']) ? $itemProperty['to_group_id'] : 0; |
||
886 | $toUserId = isset($itemProperty['to_user_id']) ? $itemProperty['to_user_id'] : null; |
||
887 | |||
888 | $insertUserId = $this->checkUserId($insertUserId); |
||
889 | $toUserId = $this->checkUserId($toUserId, true); |
||
890 | $groupInfo = $this->checkGroupId($toGroupId); |
||
891 | |||
892 | api_item_property_update( |
||
893 | $course_info, |
||
894 | TOOL_DOCUMENT, |
||
895 | $document_id, |
||
896 | 'DocumentAdded', |
||
897 | $insertUserId, |
||
898 | $groupInfo, |
||
899 | $toUserId, |
||
900 | null, |
||
901 | null, |
||
902 | $my_session_id |
||
903 | ); |
||
904 | } |
||
905 | } |
||
906 | break; |
||
907 | } // end switch |
||
908 | } else { |
||
909 | // end if file exists |
||
910 | |||
911 | //make sure the source file actually exists |
||
912 | if (is_file($this->course->backup_path.'/'.$document->path) && |
||
913 | is_readable($this->course->backup_path.'/'.$document->path) && |
||
914 | is_dir(dirname($path.$document->path)) && |
||
915 | is_writeable(dirname($path.$document->path)) |
||
916 | ) { |
||
917 | copy( |
||
918 | $this->course->backup_path.'/'.$document->path, |
||
919 | $path.$document->path |
||
920 | ); |
||
921 | |||
922 | // Replace old course code with the new destination code see BT#1985 |
||
923 | if (file_exists($path.$document->path)) { |
||
924 | $file_info = pathinfo($path.$document->path); |
||
925 | if (isset($file_info['extension']) && in_array($file_info['extension'], ['html', 'htm'])) { |
||
926 | $content = file_get_contents($path.$document->path); |
||
927 | if (UTF8_CONVERT) { |
||
928 | $content = utf8_encode($content); |
||
929 | } |
||
930 | $content = DocumentManager::replaceUrlWithNewCourseCode( |
||
931 | $content, |
||
932 | $this->course->code, |
||
933 | $this->course->destination_path, |
||
934 | $this->course->backup_path, |
||
935 | $this->course->info['path'] |
||
936 | ); |
||
937 | file_put_contents($path.$document->path, $content); |
||
938 | $this->fixEditorHtmlContent($path.$document->path, $webEditorCss); |
||
939 | } |
||
940 | } |
||
941 | |||
942 | $params = [ |
||
943 | 'c_id' => $this->destination_course_id, |
||
944 | 'path' => "/".self::DBUTF8(substr($document->path, 9)), |
||
945 | 'comment' => self::DBUTF8($document->comment), |
||
946 | 'title' => self::DBUTF8($document->title), |
||
947 | 'filetype' => self::DBUTF8($document->file_type), |
||
948 | 'size' => self::DBUTF8($document->size), |
||
949 | 'session_id' => $my_session_id, |
||
950 | 'readonly' => 0, |
||
951 | ]; |
||
952 | |||
953 | $document_id = Database::insert($table, $params); |
||
954 | |||
955 | if ($document_id) { |
||
956 | $sql = "UPDATE $table SET id = iid WHERE iid = $document_id"; |
||
957 | Database::query($sql); |
||
958 | |||
959 | $this->course->resources[RESOURCE_DOCUMENT][$id]->destination_id = $document_id; |
||
960 | |||
961 | $itemProperty = isset($document->item_properties[0]) ? $document->item_properties[0] : ''; |
||
962 | $insertUserId = isset($itemProperty['insert_user_id']) ? $itemProperty['insert_user_id'] : api_get_user_id(); |
||
963 | $toGroupId = isset($itemProperty['to_group_id']) ? $itemProperty['to_group_id'] : 0; |
||
964 | $toUserId = isset($itemProperty['to_user_id']) ? $itemProperty['to_user_id'] : null; |
||
965 | |||
966 | $insertUserId = $this->checkUserId($insertUserId); |
||
967 | $toUserId = $this->checkUserId($toUserId, true); |
||
968 | $groupInfo = $this->checkGroupId($toGroupId); |
||
969 | |||
970 | api_item_property_update( |
||
971 | $course_info, |
||
972 | TOOL_DOCUMENT, |
||
973 | $document_id, |
||
974 | 'DocumentAdded', |
||
975 | $insertUserId, |
||
976 | $groupInfo, |
||
977 | $toUserId, |
||
978 | null, |
||
979 | null, |
||
980 | $my_session_id |
||
981 | ); |
||
982 | } |
||
983 | } else { |
||
984 | // There was an error in checking existence and |
||
985 | // permissions for files to copy. Try to determine |
||
986 | // the exact issue |
||
987 | // Issue with origin document? |
||
988 | if (!is_file($this->course->backup_path.'/'.$document->path)) { |
||
989 | error_log( |
||
990 | 'Course copy generated an ignorable error while trying to copy '. |
||
991 | $this->course->backup_path.'/'.$document->path.': origin file not found' |
||
992 | ); |
||
993 | } elseif (!is_readable($this->course->backup_path.'/'.$document->path)) { |
||
994 | error_log( |
||
995 | 'Course copy generated an ignorable error while trying to copy '. |
||
996 | $this->course->backup_path.'/'.$document->path.': origin file not readable' |
||
997 | ); |
||
998 | } |
||
999 | // Issue with destination directories? |
||
1000 | if (!is_dir(dirname($path.$document->path))) { |
||
1001 | error_log( |
||
1002 | 'Course copy generated an ignorable error while trying to copy '. |
||
1003 | $this->course->backup_path.'/'.$document->path.' to '. |
||
1004 | dirname($path.$document->path).': destination directory not found' |
||
1005 | ); |
||
1006 | } |
||
1007 | if (!is_writeable(dirname($path.$document->path))) { |
||
1008 | error_log( |
||
1009 | 'Course copy generated an ignorable error while trying to copy '. |
||
1010 | $this->course->backup_path.'/'.$document->path.' to '. |
||
1011 | dirname($path.$document->path).': destination directory not writable' |
||
1012 | ); |
||
1013 | } |
||
1014 | } |
||
1015 | } // end file doesn't exist |
||
1016 | } |
||
1017 | |||
1018 | // add image information for area questions |
||
1019 | if (preg_match('/^quiz-.*$/', $document->title) && |
||
1020 | preg_match('/^document\/images\/.*$/', $document->path) |
||
1021 | ) { |
||
1022 | $this->course->resources[RESOURCE_DOCUMENT]['image_quiz'][$document->title] = [ |
||
1023 | 'path' => $document->path, |
||
1024 | 'title' => $document->title, |
||
1025 | 'source_id' => $document->source_id, |
||
1026 | 'destination_id' => $document->destination_id, |
||
1027 | ]; |
||
1028 | } |
||
1029 | } // end for each |
||
1030 | |||
1031 | // Delete sessions for the copy the new folder in session |
||
1032 | unset($_SESSION['new_base_foldername']); |
||
1033 | unset($_SESSION['orig_base_foldername']); |
||
1034 | unset($_SESSION['new_base_path']); |
||
1035 | } |
||
1036 | |||
1037 | /** |
||
1038 | * Restore scorm documents |
||
1039 | * TODO @TODO check that the restore function with renaming doesn't break the scorm structure! |
||
1040 | * see #7029. |
||
1041 | */ |
||
1042 | public function restore_scorm_documents() |
||
1043 | { |
||
1044 | $perm = api_get_permissions_for_new_directories(); |
||
1045 | if ($this->course->has_resources(RESOURCE_SCORM)) { |
||
1046 | $resources = $this->course->resources; |
||
1047 | foreach ($resources[RESOURCE_SCORM] as $document) { |
||
1048 | $path = api_get_path(SYS_COURSE_PATH).$this->course->destination_path.'/'; |
||
1049 | @mkdir(dirname($path.$document->path), $perm, true); |
||
1050 | if (file_exists($path.$document->path)) { |
||
1051 | switch ($this->file_option) { |
||
1052 | case FILE_OVERWRITE: |
||
1053 | rmdirr($path.$document->path); |
||
1054 | copyDirTo( |
||
1055 | $this->course->backup_path.'/'.$document->path, |
||
1056 | $path.$document->path, |
||
1057 | false |
||
1058 | ); |
||
1059 | break; |
||
1060 | case FILE_SKIP: |
||
1061 | break; |
||
1062 | case FILE_RENAME: |
||
1063 | $i = 1; |
||
1064 | $ext = explode('.', basename($document->path)); |
||
1065 | if (count($ext) > 1) { |
||
1066 | $ext = array_pop($ext); |
||
1067 | $file_name_no_ext = substr($document->path, 0, -(strlen($ext) + 1)); |
||
1068 | $ext = '.'.$ext; |
||
1069 | } else { |
||
1070 | $ext = ''; |
||
1071 | $file_name_no_ext = $document->path; |
||
1072 | } |
||
1073 | |||
1074 | $new_file_name = $file_name_no_ext.'_'.$i.$ext; |
||
1075 | $file_exists = file_exists($path.$new_file_name); |
||
1076 | |||
1077 | while ($file_exists) { |
||
1078 | $i++; |
||
1079 | $new_file_name = $file_name_no_ext.'_'.$i.$ext; |
||
1080 | $file_exists = file_exists($path.$new_file_name); |
||
1081 | } |
||
1082 | |||
1083 | rename( |
||
1084 | $this->course->backup_path.'/'.$document->path, |
||
1085 | $this->course->backup_path.'/'.$new_file_name |
||
1086 | ); |
||
1087 | copyDirTo( |
||
1088 | $this->course->backup_path.'/'.$new_file_name, |
||
1089 | $path.dirname($new_file_name), |
||
1090 | false |
||
1091 | ); |
||
1092 | rename( |
||
1093 | $this->course->backup_path.'/'.$new_file_name, |
||
1094 | $this->course->backup_path.'/'.$document->path |
||
1095 | ); |
||
1096 | break; |
||
1097 | } // end switch |
||
1098 | } else { |
||
1099 | // end if file exists |
||
1100 | copyDirTo( |
||
1101 | $this->course->backup_path.'/'.$document->path, |
||
1102 | $path.$document->path, |
||
1103 | false |
||
1104 | ); |
||
1105 | } |
||
1106 | } // end for each |
||
1107 | } |
||
1108 | } |
||
1109 | |||
1110 | /** |
||
1111 | * Restore forums. |
||
1112 | * |
||
1113 | * @param int $sessionId |
||
1114 | */ |
||
1115 | public function restore_forums($sessionId = 0) |
||
1116 | { |
||
1117 | if ($this->course->has_resources(RESOURCE_FORUM)) { |
||
1118 | $sessionId = (int) $sessionId; |
||
1119 | $table_forum = Database::get_course_table(TABLE_FORUM); |
||
1120 | $resources = $this->course->resources; |
||
1121 | foreach ($resources[RESOURCE_FORUM] as $id => $forum) { |
||
1122 | $params = (array) $forum->obj; |
||
1123 | $cat_id = ''; |
||
1124 | if (isset($this->course->resources[RESOURCE_FORUMCATEGORY]) && |
||
1125 | isset($this->course->resources[RESOURCE_FORUMCATEGORY][$params['forum_category']])) { |
||
1126 | if ($this->course->resources[RESOURCE_FORUMCATEGORY][$params['forum_category']]->destination_id == -1) { |
||
1127 | $cat_id = $this->restore_forum_category($params['forum_category'], $sessionId); |
||
1128 | } else { |
||
1129 | $cat_id = $this->course->resources[RESOURCE_FORUMCATEGORY][$params['forum_category']]->destination_id; |
||
1130 | } |
||
1131 | } |
||
1132 | |||
1133 | $params = self::DBUTF8_array($params); |
||
1134 | $params['c_id'] = $this->destination_course_id; |
||
1135 | $params['forum_category'] = $cat_id; |
||
1136 | $params['session_id'] = $sessionId; |
||
1137 | $params['start_time'] = isset($params['start_time']) && $params['start_time'] === '0000-00-00 00:00:00' ? null : $params['start_time']; |
||
1138 | $params['end_time'] = isset($params['end_time']) && $params['end_time'] === '0000-00-00 00:00:00' ? null : $params['end_time']; |
||
1139 | $params['forum_id'] = 0; |
||
1140 | unset($params['iid']); |
||
1141 | |||
1142 | $params['forum_comment'] = DocumentManager::replaceUrlWithNewCourseCode( |
||
1143 | $params['forum_comment'], |
||
1144 | $this->course->code, |
||
1145 | $this->course->destination_path, |
||
1146 | $this->course->backup_path, |
||
1147 | $this->course->info['path'] |
||
1148 | ); |
||
1149 | |||
1150 | if (!empty($params['forum_image'])) { |
||
1151 | $original_forum_image = $this->course->path.'upload/forum/images/'.$params['forum_image']; |
||
1152 | if (file_exists($original_forum_image)) { |
||
1153 | $new_forum_image = api_get_path(SYS_COURSE_PATH). |
||
1154 | $this->destination_course_info['path'].'/upload/forum/images/'.$params['forum_image']; |
||
1155 | @copy($original_forum_image, $new_forum_image); |
||
1156 | } |
||
1157 | } |
||
1158 | |||
1159 | $new_id = Database::insert($table_forum, $params); |
||
1160 | |||
1161 | if ($new_id) { |
||
1162 | $sql = "UPDATE $table_forum SET forum_id = iid WHERE iid = $new_id"; |
||
1163 | Database::query($sql); |
||
1164 | |||
1165 | api_item_property_update( |
||
1166 | $this->destination_course_info, |
||
1167 | TOOL_FORUM, |
||
1168 | $new_id, |
||
1169 | 'ForumUpdated', |
||
1170 | api_get_user_id(), |
||
1171 | null, |
||
1172 | null, |
||
1173 | null, |
||
1174 | null, |
||
1175 | $sessionId |
||
1176 | ); |
||
1177 | |||
1178 | $this->course->resources[RESOURCE_FORUM][$id]->destination_id = $new_id; |
||
1179 | $forum_topics = 0; |
||
1180 | if (isset($this->course->resources[RESOURCE_FORUMTOPIC]) && |
||
1181 | is_array($this->course->resources[RESOURCE_FORUMTOPIC]) |
||
1182 | ) { |
||
1183 | foreach ($this->course->resources[RESOURCE_FORUMTOPIC] as $topic_id => $topic) { |
||
1184 | if ($topic->obj->forum_id == $id) { |
||
1185 | $this->restore_topic($topic_id, $new_id, $sessionId); |
||
1186 | $forum_topics++; |
||
1187 | } |
||
1188 | } |
||
1189 | } |
||
1190 | if ($forum_topics > 0) { |
||
1191 | $sql = "UPDATE ".$table_forum." SET forum_threads = ".$forum_topics." |
||
1192 | WHERE c_id = {$this->destination_course_id} AND forum_id = ".(int) $new_id; |
||
1193 | Database::query($sql); |
||
1194 | } |
||
1195 | } |
||
1196 | } |
||
1197 | } |
||
1198 | } |
||
1199 | |||
1200 | /** |
||
1201 | * Restore forum-categories. |
||
1202 | */ |
||
1203 | public function restore_forum_category($my_id = null, $sessionId = 0) |
||
1204 | { |
||
1205 | $forum_cat_table = Database::get_course_table(TABLE_FORUM_CATEGORY); |
||
1206 | $resources = $this->course->resources; |
||
1207 | $sessionId = (int) $sessionId; |
||
1208 | if (!empty($resources[RESOURCE_FORUMCATEGORY])) { |
||
1209 | foreach ($resources[RESOURCE_FORUMCATEGORY] as $id => $forum_cat) { |
||
1210 | if (!empty($my_id)) { |
||
1211 | if ($my_id != $id) { |
||
1212 | continue; |
||
1213 | } |
||
1214 | } |
||
1215 | if ($forum_cat && !$forum_cat->is_restored()) { |
||
1216 | $params = (array) $forum_cat->obj; |
||
1217 | $params['c_id'] = $this->destination_course_id; |
||
1218 | $params['cat_comment'] = DocumentManager::replaceUrlWithNewCourseCode( |
||
1219 | $params['cat_comment'], |
||
1220 | $this->course->code, |
||
1221 | $this->course->destination_path, |
||
1222 | $this->course->backup_path, |
||
1223 | $this->course->info['path'] |
||
1224 | ); |
||
1225 | $params['session_id'] = $sessionId; |
||
1226 | $params['cat_id'] = 0; |
||
1227 | unset($params['iid']); |
||
1228 | |||
1229 | $params = self::DBUTF8_array($params); |
||
1230 | $new_id = Database::insert($forum_cat_table, $params); |
||
1231 | |||
1232 | if ($new_id) { |
||
1233 | $sql = "UPDATE $forum_cat_table SET cat_id = iid WHERE iid = $new_id"; |
||
1234 | Database::query($sql); |
||
1235 | |||
1236 | api_item_property_update( |
||
1237 | $this->destination_course_info, |
||
1238 | TOOL_FORUM_CATEGORY, |
||
1239 | $new_id, |
||
1240 | 'ForumCategoryUpdated', |
||
1241 | api_get_user_id(), |
||
1242 | null, |
||
1243 | null, |
||
1244 | null, |
||
1245 | null, |
||
1246 | $sessionId |
||
1247 | ); |
||
1248 | $this->course->resources[RESOURCE_FORUMCATEGORY][$id]->destination_id = $new_id; |
||
1249 | } |
||
1250 | |||
1251 | if (!empty($my_id)) { |
||
1252 | return $new_id; |
||
1253 | } |
||
1254 | } |
||
1255 | } |
||
1256 | } |
||
1257 | } |
||
1258 | |||
1259 | /** |
||
1260 | * Restore a forum-topic. |
||
1261 | * |
||
1262 | * @param false|string $forum_id |
||
1263 | * |
||
1264 | * @return int |
||
1265 | */ |
||
1266 | public function restore_topic($thread_id, $forum_id, $sessionId = 0) |
||
1267 | { |
||
1268 | $table = Database::get_course_table(TABLE_FORUM_THREAD); |
||
1269 | $topic = $this->course->resources[RESOURCE_FORUMTOPIC][$thread_id]; |
||
1270 | |||
1271 | $sessionId = (int) $sessionId; |
||
1272 | $params = (array) $topic->obj; |
||
1273 | |||
1274 | $params = self::DBUTF8_array($params); |
||
1275 | $params['c_id'] = $this->destination_course_id; |
||
1276 | $params['forum_id'] = $forum_id; |
||
1277 | $params['thread_poster_id'] = $this->first_teacher_id; |
||
1278 | $params['thread_date'] = api_get_utc_datetime(); |
||
1279 | $params['thread_close_date'] = null; |
||
1280 | $params['thread_last_post'] = 0; |
||
1281 | $params['thread_replies'] = 0; |
||
1282 | $params['thread_views'] = 0; |
||
1283 | $params['session_id'] = $sessionId; |
||
1284 | $params['thread_id'] = 0; |
||
1285 | |||
1286 | unset($params['iid']); |
||
1287 | |||
1288 | $new_id = Database::insert($table, $params); |
||
1289 | |||
1290 | if ($new_id) { |
||
1291 | $sql = "UPDATE $table SET thread_id = iid WHERE iid = $new_id"; |
||
1292 | Database::query($sql); |
||
1293 | |||
1294 | api_item_property_update( |
||
1295 | $this->destination_course_info, |
||
1296 | TOOL_FORUM_THREAD, |
||
1297 | $new_id, |
||
1298 | 'ThreadAdded', |
||
1299 | api_get_user_id(), |
||
1300 | 0, |
||
1301 | 0, |
||
1302 | null, |
||
1303 | null, |
||
1304 | $sessionId |
||
1305 | ); |
||
1306 | |||
1307 | $this->course->resources[RESOURCE_FORUMTOPIC][$thread_id]->destination_id = $new_id; |
||
1308 | $topic_replies = -1; |
||
1309 | |||
1310 | foreach ($this->course->resources[RESOURCE_FORUMPOST] as $post_id => $post) { |
||
1311 | if ($post->obj->thread_id == $thread_id) { |
||
1312 | $topic_replies++; |
||
1313 | $this->restore_post($post_id, $new_id, $forum_id, $sessionId); |
||
1314 | } |
||
1315 | } |
||
1316 | } |
||
1317 | |||
1318 | return $new_id; |
||
1319 | } |
||
1320 | |||
1321 | /** |
||
1322 | * Restore a forum-post. |
||
1323 | * |
||
1324 | * @TODO Restore tree-structure of posts. For example: attachments to posts. |
||
1325 | * |
||
1326 | * @param false|string $topic_id |
||
1327 | * |
||
1328 | * @return int |
||
1329 | */ |
||
1330 | public function restore_post($id, $topic_id, $forum_id, $sessionId = 0) |
||
1331 | { |
||
1332 | $table_post = Database::get_course_table(TABLE_FORUM_POST); |
||
1333 | $post = $this->course->resources[RESOURCE_FORUMPOST][$id]; |
||
1334 | $params = (array) $post->obj; |
||
1335 | $params['c_id'] = $this->destination_course_id; |
||
1336 | $params['forum_id'] = $forum_id; |
||
1337 | $params['thread_id'] = $topic_id; |
||
1338 | $params['poster_id'] = $this->first_teacher_id; |
||
1339 | $params['post_date'] = api_get_utc_datetime(); |
||
1340 | $params['post_id'] = 0; |
||
1341 | unset($params['iid']); |
||
1342 | |||
1343 | $params['post_text'] = DocumentManager::replaceUrlWithNewCourseCode( |
||
1344 | $params['post_text'], |
||
1345 | $this->course->code, |
||
1346 | $this->course->destination_path, |
||
1347 | $this->course->backup_path, |
||
1348 | $this->course->info['path'] |
||
1349 | ); |
||
1350 | $new_id = Database::insert($table_post, $params); |
||
1351 | |||
1352 | if ($new_id) { |
||
1353 | $sql = "UPDATE $table_post SET post_id = iid WHERE iid = $new_id"; |
||
1354 | Database::query($sql); |
||
1355 | |||
1356 | api_item_property_update( |
||
1357 | $this->destination_course_info, |
||
1358 | TOOL_FORUM_POST, |
||
1359 | $new_id, |
||
1360 | 'PostAdded', |
||
1361 | api_get_user_id(), |
||
1362 | 0, |
||
1363 | 0, |
||
1364 | null, |
||
1365 | null, |
||
1366 | $sessionId |
||
1367 | ); |
||
1368 | $this->course->resources[RESOURCE_FORUMPOST][$id]->destination_id = $new_id; |
||
1369 | } |
||
1370 | |||
1371 | return $new_id; |
||
1372 | } |
||
1373 | |||
1374 | /** |
||
1375 | * Restore links. |
||
1376 | */ |
||
1377 | public function restore_links($session_id = 0) |
||
1430 | } |
||
1431 | } |
||
1432 | } |
||
1433 | } |
||
1434 | |||
1435 | /** |
||
1436 | * Restore a link-category. |
||
1437 | * |
||
1438 | * @param int |
||
1439 | * @param int |
||
1440 | * |
||
1441 | * @return bool |
||
1442 | */ |
||
1443 | public function restore_link_category($id, $sessionId = 0) |
||
1444 | { |
||
1445 | $params = []; |
||
1446 | $sessionId = (int) $sessionId; |
||
1447 | if (!empty($sessionId)) { |
||
1448 | $params['session_id'] = $sessionId; |
||
1449 | } |
||
1450 | |||
1451 | if ($id == 0) { |
||
1452 | return 0; |
||
1453 | } |
||
1454 | $link_cat_table = Database::get_course_table(TABLE_LINK_CATEGORY); |
||
1455 | $resources = $this->course->resources; |
||
1456 | $link_cat = $resources[RESOURCE_LINKCATEGORY][$id]; |
||
1457 | if (is_object($link_cat) && !$link_cat->is_restored()) { |
||
1458 | $sql = "SELECT MAX(display_order) FROM $link_cat_table |
||
1459 | WHERE c_id = ".$this->destination_course_id; |
||
1460 | $result = Database::query($sql); |
||
1461 | [$orderMax] = Database::fetch_array($result, 'NUM'); |
||
1462 | $display_order = $orderMax + 1; |
||
1463 | |||
1464 | $params['c_id'] = $this->destination_course_id; |
||
1465 | $params['category_title'] = self::DBUTF8($link_cat->title); |
||
1466 | $params['description'] = self::DBUTF8($link_cat->description); |
||
1467 | $params['display_order'] = $display_order; |
||
1468 | $new_id = Database::insert($link_cat_table, $params); |
||
1469 | |||
1470 | if ($new_id) { |
||
1471 | $sql = "UPDATE $link_cat_table |
||
1472 | SET id = iid |
||
1473 | WHERE iid = $new_id"; |
||
1474 | Database::query($sql); |
||
1475 | |||
1476 | $courseInfo = api_get_course_info_by_id($this->destination_course_id); |
||
1477 | api_item_property_update( |
||
1478 | $courseInfo, |
||
1479 | TOOL_LINK_CATEGORY, |
||
1480 | $new_id, |
||
1481 | 'LinkCategoryAdded', |
||
1482 | api_get_user_id(), |
||
1483 | null, |
||
1484 | null, |
||
1485 | null, |
||
1486 | null, |
||
1487 | $sessionId |
||
1488 | ); |
||
1489 | api_set_default_visibility( |
||
1490 | $new_id, |
||
1491 | TOOL_LINK_CATEGORY, |
||
1492 | 0, |
||
1493 | $courseInfo, |
||
1494 | $sessionId |
||
1495 | ); |
||
1496 | } |
||
1497 | |||
1498 | $this->course->resources[RESOURCE_LINKCATEGORY][$id]->destination_id = $new_id; |
||
1499 | |||
1500 | return $new_id; |
||
1501 | } |
||
1502 | |||
1503 | return $this->course->resources[RESOURCE_LINKCATEGORY][$id]->destination_id; |
||
1504 | } |
||
1505 | |||
1506 | /** |
||
1507 | * Restore tool intro. |
||
1508 | * |
||
1509 | * @param int |
||
1510 | */ |
||
1511 | public function restore_tool_intro($sessionId = 0) |
||
1512 | { |
||
1513 | if ($this->course->has_resources(RESOURCE_TOOL_INTRO)) { |
||
1514 | $sessionId = (int) $sessionId; |
||
1515 | $tool_intro_table = Database::get_course_table(TABLE_TOOL_INTRO); |
||
1516 | $resources = $this->course->resources; |
||
1517 | foreach ($resources[RESOURCE_TOOL_INTRO] as $id => $tool_intro) { |
||
1518 | $sql = "DELETE FROM $tool_intro_table |
||
1519 | WHERE |
||
1520 | c_id = ".$this->destination_course_id." AND |
||
1521 | id='".self::DBUTF8escapestring($tool_intro->id)."'"; |
||
1522 | Database::query($sql); |
||
1523 | |||
1524 | $tool_intro->intro_text = DocumentManager::replaceUrlWithNewCourseCode( |
||
1525 | $tool_intro->intro_text, |
||
1526 | $this->course->code, |
||
1527 | $this->course->destination_path, |
||
1528 | $this->course->backup_path, |
||
1529 | $this->course->info['path'] |
||
1530 | ); |
||
1531 | |||
1532 | $params = [ |
||
1533 | 'c_id' => $this->destination_course_id, |
||
1534 | 'id' => ($tool_intro->id === false ? '' : self::DBUTF8($tool_intro->id)), |
||
1535 | 'intro_text' => self::DBUTF8($tool_intro->intro_text), |
||
1536 | 'session_id' => $sessionId, |
||
1537 | ]; |
||
1538 | |||
1539 | $id = Database::insert($tool_intro_table, $params); |
||
1540 | if ($id) { |
||
1541 | if (!isset($this->course->resources[RESOURCE_TOOL_INTRO][$id])) { |
||
1542 | $this->course->resources[RESOURCE_TOOL_INTRO][$id] = new stdClass(); |
||
1543 | } |
||
1544 | |||
1545 | $this->course->resources[RESOURCE_TOOL_INTRO][$id]->destination_id = $id; |
||
1546 | } |
||
1547 | } |
||
1548 | } |
||
1549 | } |
||
1550 | |||
1551 | /** |
||
1552 | * Restore events. |
||
1553 | * |
||
1554 | * @param int |
||
1555 | */ |
||
1556 | public function restore_events($sessionId = 0) |
||
1557 | { |
||
1558 | if ($this->course->has_resources(RESOURCE_EVENT)) { |
||
1559 | $sessionId = (int) $sessionId; |
||
1560 | $table = Database::get_course_table(TABLE_AGENDA); |
||
1561 | $resources = $this->course->resources; |
||
1562 | foreach ($resources[RESOURCE_EVENT] as $id => $event) { |
||
1563 | // check resources inside html from ckeditor tool and copy correct urls into recipient course |
||
1564 | $event->content = DocumentManager::replaceUrlWithNewCourseCode( |
||
1565 | $event->content, |
||
1566 | $this->course->code, |
||
1567 | $this->course->destination_path, |
||
1568 | $this->course->backup_path, |
||
1569 | $this->course->info['path'] |
||
1570 | ); |
||
1571 | |||
1572 | $params = [ |
||
1573 | 'c_id' => $this->destination_course_id, |
||
1574 | 'title' => self::DBUTF8($event->title), |
||
1575 | 'content' => ($event->content === false ? '' : self::DBUTF8($event->content)), |
||
1576 | 'all_day' => $event->all_day, |
||
1577 | 'start_date' => $event->start_date, |
||
1578 | 'end_date' => $event->end_date, |
||
1579 | 'session_id' => $sessionId, |
||
1580 | ]; |
||
1581 | $new_event_id = Database::insert($table, $params); |
||
1582 | |||
1583 | if ($new_event_id) { |
||
1584 | $sql = "UPDATE $table SET id = iid WHERE iid = $new_event_id"; |
||
1585 | Database::query($sql); |
||
1586 | |||
1587 | if (!isset($this->course->resources[RESOURCE_EVENT][$id])) { |
||
1588 | $this->course->resources[RESOURCE_EVENT][$id] = new stdClass(); |
||
1589 | } |
||
1590 | $this->course->resources[RESOURCE_EVENT][$id]->destination_id = $new_event_id; |
||
1591 | } |
||
1592 | |||
1593 | // Copy event attachment |
||
1594 | $origin_path = $this->course->backup_path.'/upload/calendar/'; |
||
1595 | $destination_path = api_get_path(SYS_COURSE_PATH).$this->course->destination_path.'/upload/calendar/'; |
||
1596 | |||
1597 | if (!empty($this->course->orig)) { |
||
1598 | $table_attachment = Database::get_course_table(TABLE_AGENDA_ATTACHMENT); |
||
1599 | $sql = 'SELECT path, comment, size, filename |
||
1600 | FROM '.$table_attachment.' |
||
1601 | WHERE c_id = '.$this->destination_course_id.' AND agenda_id = '.$id; |
||
1602 | $attachment_event = Database::query($sql); |
||
1603 | $attachment_event = Database::fetch_object($attachment_event); |
||
1604 | |||
1605 | if (file_exists($origin_path.$attachment_event->path) && |
||
1606 | !is_dir($origin_path.$attachment_event->path) |
||
1607 | ) { |
||
1608 | $new_filename = uniqid(''); //ass seen in the add_agenda_attachment_file() function in agenda.inc.php |
||
1609 | $copy_result = copy( |
||
1610 | $origin_path.$attachment_event->path, |
||
1611 | $destination_path.$new_filename |
||
1612 | ); |
||
1613 | //$copy_result = true; |
||
1614 | if ($copy_result) { |
||
1615 | $table_attachment = Database::get_course_table(TABLE_AGENDA_ATTACHMENT); |
||
1616 | |||
1617 | $params = [ |
||
1618 | 'c_id' => $this->destination_course_id, |
||
1619 | 'path' => self::DBUTF8($new_filename), |
||
1620 | 'comment' => self::DBUTF8($attachment_event->comment), |
||
1621 | 'size' => isset($attachment_event->size) ? $attachment_event->size : '', |
||
1622 | 'filename' => isset($attachment_event->filename) ? $attachment_event->filename : '', |
||
1623 | 'agenda_id' => $new_event_id, |
||
1624 | ]; |
||
1625 | $id = Database::insert($table_attachment, $params); |
||
1626 | if ($id) { |
||
1627 | $sql = "UPDATE $table_attachment SET id = iid WHERE iid = $id"; |
||
1628 | Database::query($sql); |
||
1629 | } |
||
1630 | } |
||
1631 | } |
||
1632 | } else { |
||
1633 | // get the info of the file |
||
1634 | if (!empty($event->attachment_path) && |
||
1635 | is_file($origin_path.$event->attachment_path) && |
||
1636 | is_readable($origin_path.$event->attachment_path) |
||
1637 | ) { |
||
1638 | $new_filename = uniqid(''); //ass seen in the add_agenda_attachment_file() function in agenda.inc.php |
||
1639 | $copy_result = copy( |
||
1640 | $origin_path.$event->attachment_path, |
||
1641 | $destination_path.$new_filename |
||
1642 | ); |
||
1643 | if ($copy_result) { |
||
1644 | $table_attachment = Database::get_course_table(TABLE_AGENDA_ATTACHMENT); |
||
1645 | |||
1646 | $params = [ |
||
1647 | 'c_id' => $this->destination_course_id, |
||
1648 | 'path' => self::DBUTF8($new_filename), |
||
1649 | 'comment' => self::DBUTF8($event->attachment_comment), |
||
1650 | 'size' => isset($event->size) ? $event->size : '', |
||
1651 | 'filename' => isset($event->filename) ? $event->filename : '', |
||
1652 | 'agenda_id' => $new_event_id, |
||
1653 | ]; |
||
1654 | $id = Database::insert($table_attachment, $params); |
||
1655 | |||
1656 | if ($id) { |
||
1657 | $sql = "UPDATE $table_attachment SET id = iid WHERE iid = $id"; |
||
1658 | Database::query($sql); |
||
1659 | } |
||
1660 | } |
||
1661 | } |
||
1662 | } |
||
1663 | } |
||
1664 | } |
||
1665 | } |
||
1666 | |||
1667 | /** |
||
1668 | * Restore course-description. |
||
1669 | * |
||
1670 | * @param int |
||
1671 | */ |
||
1672 | public function restore_course_descriptions($session_id = 0) |
||
1673 | { |
||
1674 | if ($this->course->has_resources(RESOURCE_COURSEDESCRIPTION)) { |
||
1675 | $table = Database::get_course_table(TABLE_COURSE_DESCRIPTION); |
||
1676 | $resources = $this->course->resources; |
||
1677 | foreach ($resources[RESOURCE_COURSEDESCRIPTION] as $id => $cd) { |
||
1678 | $courseDescription = (array) $cd; |
||
1679 | |||
1680 | $content = isset($courseDescription['content']) ? $courseDescription['content'] : ''; |
||
1681 | $descriptionType = isset($courseDescription['description_type']) ? $courseDescription['description_type'] : ''; |
||
1682 | $title = isset($courseDescription['title']) ? $courseDescription['title'] : ''; |
||
1683 | |||
1684 | // check resources inside html from ckeditor tool and copy correct urls into recipient course |
||
1685 | $description_content = DocumentManager::replaceUrlWithNewCourseCode( |
||
1686 | $content, |
||
1687 | $this->course->code, |
||
1688 | $this->course->destination_path, |
||
1689 | $this->course->backup_path, |
||
1690 | $this->course->info['path'] |
||
1691 | ); |
||
1692 | |||
1693 | $params = []; |
||
1694 | $session_id = (int) $session_id; |
||
1695 | $params['session_id'] = $session_id; |
||
1696 | $params['c_id'] = $this->destination_course_id; |
||
1697 | $params['description_type'] = self::DBUTF8($descriptionType); |
||
1698 | $params['title'] = self::DBUTF8($title); |
||
1699 | $params['content'] = ($description_content === false ? '' : self::DBUTF8($description_content)); |
||
1700 | $params['progress'] = 0; |
||
1701 | |||
1702 | $id = Database::insert($table, $params); |
||
1703 | if ($id) { |
||
1704 | $sql = "UPDATE $table SET id = iid WHERE iid = $id"; |
||
1705 | Database::query($sql); |
||
1706 | |||
1707 | if (!isset($this->course->resources[RESOURCE_COURSEDESCRIPTION][$id])) { |
||
1708 | $this->course->resources[RESOURCE_COURSEDESCRIPTION][$id] = new stdClass(); |
||
1709 | } |
||
1710 | $this->course->resources[RESOURCE_COURSEDESCRIPTION][$id]->destination_id = $id; |
||
1711 | } |
||
1712 | } |
||
1713 | } |
||
1714 | } |
||
1715 | |||
1716 | /** |
||
1717 | * Restore announcements. |
||
1718 | * |
||
1719 | * @param int |
||
1720 | */ |
||
1721 | public function restore_announcements($sessionId = 0) |
||
1722 | { |
||
1723 | if ($this->course->has_resources(RESOURCE_ANNOUNCEMENT)) { |
||
1724 | $sessionId = (int) $sessionId; |
||
1725 | $table = Database::get_course_table(TABLE_ANNOUNCEMENT); |
||
1726 | $resources = $this->course->resources; |
||
1727 | foreach ($resources[RESOURCE_ANNOUNCEMENT] as $id => $announcement) { |
||
1728 | // check resources inside html from ckeditor tool and copy correct urls into recipient course |
||
1729 | $announcement->content = DocumentManager::replaceUrlWithNewCourseCode( |
||
1730 | $announcement->content, |
||
1731 | $this->course->code, |
||
1732 | $this->course->destination_path, |
||
1733 | $this->course->backup_path, |
||
1734 | $this->course->info['path'] |
||
1735 | ); |
||
1736 | |||
1737 | $params = [ |
||
1738 | 'c_id' => $this->destination_course_id, |
||
1739 | 'title' => self::DBUTF8($announcement->title), |
||
1740 | 'content' => ($announcement->content === false ? '' : self::DBUTF8($announcement->content)), |
||
1741 | 'end_date' => $announcement->date, |
||
1742 | 'display_order' => $announcement->display_order, |
||
1743 | 'email_sent' => $announcement->email_sent, |
||
1744 | 'session_id' => $sessionId, |
||
1745 | ]; |
||
1746 | |||
1747 | $new_announcement_id = Database::insert($table, $params); |
||
1748 | |||
1749 | if ($new_announcement_id) { |
||
1750 | $sql = "UPDATE $table SET id = iid WHERE iid = $new_announcement_id"; |
||
1751 | Database::query($sql); |
||
1752 | |||
1753 | if (!isset($this->course->resources[RESOURCE_ANNOUNCEMENT][$id])) { |
||
1754 | $this->course->resources[RESOURCE_ANNOUNCEMENT][$id] = new stdClass(); |
||
1755 | } |
||
1756 | $this->course->resources[RESOURCE_ANNOUNCEMENT][$id]->destination_id = $new_announcement_id; |
||
1757 | } |
||
1758 | |||
1759 | $origin_path = $this->course->backup_path.'/upload/announcements/'; |
||
1760 | $destination_path = api_get_path(SYS_COURSE_PATH).$this->course->destination_path.'/upload/announcements/'; |
||
1761 | |||
1762 | // Copy announcement attachment file |
||
1763 | if (!empty($this->course->orig)) { |
||
1764 | $table_attachment = Database::get_course_table(TABLE_ANNOUNCEMENT_ATTACHMENT); |
||
1765 | $sql = 'SELECT path, comment, size, filename |
||
1766 | FROM '.$table_attachment.' |
||
1767 | WHERE |
||
1768 | c_id = '.$this->destination_course_id.' AND |
||
1769 | announcement_id = '.$id; |
||
1770 | $attachment_event = Database::query($sql); |
||
1771 | $attachment_event = Database::fetch_object($attachment_event); |
||
1772 | |||
1773 | if (file_exists($origin_path.$attachment_event->path) && |
||
1774 | !is_dir($origin_path.$attachment_event->path) |
||
1775 | ) { |
||
1776 | $new_filename = uniqid(''); //ass seen in the add_agenda_attachment_file() function in agenda.inc.php |
||
1777 | $copy_result = copy( |
||
1778 | $origin_path.$attachment_event->path, |
||
1779 | $destination_path.$new_filename |
||
1780 | ); |
||
1781 | |||
1782 | if ($copy_result) { |
||
1783 | $table_attachment = Database::get_course_table(TABLE_ANNOUNCEMENT_ATTACHMENT); |
||
1784 | |||
1785 | $params = [ |
||
1786 | 'c_id' => $this->destination_course_id, |
||
1787 | 'path' => self::DBUTF8($new_filename), |
||
1788 | 'comment' => self::DBUTF8($attachment_event->comment), |
||
1789 | 'size' => $attachment_event->size, |
||
1790 | 'filename' => $attachment_event->filename, |
||
1791 | 'announcement_id' => $new_announcement_id, |
||
1792 | ]; |
||
1793 | |||
1794 | $attachmentId = Database::insert($table_attachment, $params); |
||
1795 | |||
1796 | if ($attachmentId) { |
||
1797 | $sql = "UPDATE $table_attachment SET id = iid WHERE iid = $attachmentId"; |
||
1798 | Database::query($sql); |
||
1799 | } |
||
1800 | } |
||
1801 | } |
||
1802 | } else { |
||
1803 | // get the info of the file |
||
1804 | if (!empty($announcement->attachment_path) && |
||
1805 | is_file($origin_path.$announcement->attachment_path) && |
||
1806 | is_readable($origin_path.$announcement->attachment_path) |
||
1807 | ) { |
||
1808 | $new_filename = uniqid(''); //ass seen in the add_agenda_attachment_file() function in agenda.inc.php |
||
1809 | $copy_result = copy($origin_path.$announcement->attachment_path, $destination_path.$new_filename); |
||
1810 | |||
1811 | if ($copy_result) { |
||
1812 | $table_attachment = Database::get_course_table(TABLE_ANNOUNCEMENT_ATTACHMENT); |
||
1813 | |||
1814 | $params = [ |
||
1815 | 'c_id' => $this->destination_course_id, |
||
1816 | 'path' => self::DBUTF8($new_filename), |
||
1817 | 'comment' => self::DBUTF8($announcement->attachment_comment), |
||
1818 | 'size' => $announcement->attachment_size, |
||
1819 | 'filename' => $announcement->attachment_filename, |
||
1820 | 'announcement_id' => $new_announcement_id, |
||
1821 | ]; |
||
1822 | |||
1823 | $attachmentId = Database::insert($table_attachment, $params); |
||
1824 | |||
1825 | if ($attachmentId) { |
||
1826 | $sql = "UPDATE $table_attachment SET id = iid WHERE iid = $attachmentId"; |
||
1827 | Database::query($sql); |
||
1828 | } |
||
1829 | } |
||
1830 | } |
||
1831 | } |
||
1832 | } |
||
1833 | } |
||
1834 | } |
||
1835 | |||
1836 | /** |
||
1837 | * Restore Quiz. |
||
1838 | * |
||
1839 | * @param int $session_id |
||
1840 | * @param bool $respect_base_content |
||
1841 | */ |
||
1842 | public function restore_quizzes( |
||
1843 | $session_id = 0, |
||
1844 | $respect_base_content = false |
||
1845 | ) { |
||
1846 | if ($this->course->has_resources(RESOURCE_QUIZ)) { |
||
1847 | $table_qui = Database::get_course_table(TABLE_QUIZ_TEST); |
||
1848 | $table_rel = Database::get_course_table(TABLE_QUIZ_TEST_QUESTION); |
||
1849 | $table_doc = Database::get_course_table(TABLE_DOCUMENT); |
||
1850 | $resources = $this->course->resources; |
||
1851 | // Check if the "id" column still exists |
||
1852 | $idColumn = true; |
||
1853 | $columns = Database::listTableColumns($table_qui); |
||
1854 | if (!in_array('id', array_keys($columns))) { |
||
1855 | $idColumn = false; |
||
1856 | } |
||
1857 | |||
1858 | foreach ($resources[RESOURCE_QUIZ] as $id => $quiz) { |
||
1859 | if (isset($quiz->obj)) { |
||
1860 | // For new imports |
||
1861 | $quiz = $quiz->obj; |
||
1862 | } else { |
||
1863 | // For backward compatibility |
||
1864 | $quiz->obj = $quiz; |
||
1865 | } |
||
1866 | |||
1867 | $doc = ''; |
||
1868 | if (!empty($quiz->sound)) { |
||
1869 | if (isset($this->course->resources[RESOURCE_DOCUMENT][$quiz->sound]) && |
||
1870 | $this->course->resources[RESOURCE_DOCUMENT][$quiz->sound]->is_restored()) { |
||
1871 | $sql = "SELECT path FROM $table_doc |
||
1872 | WHERE |
||
1873 | c_id = ".$this->destination_course_id." AND |
||
1874 | id = ".$resources[RESOURCE_DOCUMENT][$quiz->sound]->destination_id; |
||
1875 | $doc = Database::query($sql); |
||
1876 | $doc = Database::fetch_object($doc); |
||
1877 | $doc = str_replace('/audio/', '', $doc->path); |
||
1878 | } |
||
1879 | } |
||
1880 | |||
1881 | if ($id != -1) { |
||
1882 | // check resources inside html from ckeditor tool and copy correct urls into recipient course |
||
1883 | $quiz->description = DocumentManager::replaceUrlWithNewCourseCode( |
||
1884 | $quiz->description, |
||
1885 | $this->course->code, |
||
1886 | $this->course->destination_path, |
||
1887 | $this->course->backup_path, |
||
1888 | $this->course->info['path'] |
||
1889 | ); |
||
1890 | |||
1891 | $quiz->start_time = $quiz->start_time == '0000-00-00 00:00:00' ? null : $quiz->start_time; |
||
1892 | $quiz->end_time = $quiz->end_time == '0000-00-00 00:00:00' ? null : $quiz->end_time; |
||
1893 | |||
1894 | global $_custom; |
||
1895 | if (isset($_custom['exercises_clean_dates_when_restoring']) && |
||
1896 | $_custom['exercises_clean_dates_when_restoring'] |
||
1897 | ) { |
||
1898 | $quiz->start_time = null; |
||
1899 | $quiz->end_time = null; |
||
1900 | } |
||
1901 | |||
1902 | $params = [ |
||
1903 | 'c_id' => $this->destination_course_id, |
||
1904 | 'title' => self::DBUTF8($quiz->title), |
||
1905 | 'description' => ($quiz->description === false ? '' : self::DBUTF8($quiz->description)), |
||
1906 | 'type' => isset($quiz->quiz_type) ? (int) $quiz->quiz_type : $quiz->type, |
||
1907 | 'random' => (int) $quiz->random, |
||
1908 | 'active' => $quiz->active, |
||
1909 | 'sound' => self::DBUTF8($doc), |
||
1910 | 'max_attempt' => (int) $quiz->max_attempt, |
||
1911 | 'results_disabled' => (int) $quiz->results_disabled, |
||
1912 | 'access_condition' => $quiz->access_condition, |
||
1913 | 'pass_percentage' => $quiz->pass_percentage, |
||
1914 | 'feedback_type' => (int) $quiz->feedback_type, |
||
1915 | 'random_answers' => (int) $quiz->random_answers, |
||
1916 | 'random_by_category' => (int) $quiz->random_by_category, |
||
1917 | 'review_answers' => (int) $quiz->review_answers, |
||
1918 | 'propagate_neg' => (int) $quiz->propagate_neg, |
||
1919 | 'text_when_finished' => (string) $quiz->text_when_finished, |
||
1920 | 'expired_time' => (int) $quiz->expired_time, |
||
1921 | 'start_time' => $quiz->start_time, |
||
1922 | 'end_time' => $quiz->end_time, |
||
1923 | 'display_category_name' => 0, |
||
1924 | 'save_correct_answers' => isset($quiz->save_correct_answers) ? $quiz->save_correct_answers : 0, |
||
1925 | 'hide_question_title' => isset($quiz->hide_question_title) ? $quiz->hide_question_title : 0, |
||
1926 | ]; |
||
1927 | |||
1928 | $allow = api_get_configuration_value('allow_notification_setting_per_exercise'); |
||
1929 | if ($allow) { |
||
1930 | $params['notifications'] = isset($quiz->notifications) ? $quiz->notifications : ''; |
||
1931 | } |
||
1932 | |||
1933 | if ($respect_base_content) { |
||
1934 | $my_session_id = $quiz->session_id; |
||
1935 | if (!empty($quiz->session_id)) { |
||
1936 | $my_session_id = $session_id; |
||
1937 | } |
||
1938 | $params['session_id'] = $my_session_id; |
||
1939 | } else { |
||
1940 | if (!empty($session_id)) { |
||
1941 | $session_id = (int) $session_id; |
||
1942 | $params['session_id'] = $session_id; |
||
1943 | } |
||
1944 | } |
||
1945 | $new_id = Database::insert($table_qui, $params); |
||
1946 | |||
1947 | if ($new_id && $idColumn) { |
||
1948 | $sql = "UPDATE $table_qui SET id = iid WHERE iid = $new_id"; |
||
1949 | Database::query($sql); |
||
1950 | } |
||
1951 | } else { |
||
1952 | // $id = -1 identifies the fictional test for collecting |
||
1953 | // orphan questions. We do not store it in the database. |
||
1954 | $new_id = -1; |
||
1955 | } |
||
1956 | |||
1957 | $this->course->resources[RESOURCE_QUIZ][$id]->destination_id = $new_id; |
||
1958 | $order = 0; |
||
1959 | if (!empty($quiz->question_ids)) { |
||
1960 | foreach ($quiz->question_ids as $index => $question_id) { |
||
1961 | $qid = $this->restore_quiz_question($question_id, $idColumn); |
||
1962 | $question_order = $quiz->question_orders[$index] ? $quiz->question_orders[$index] : ++$order; |
||
1963 | $sql = "INSERT IGNORE INTO $table_rel SET |
||
1964 | c_id = ".$this->destination_course_id.", |
||
1965 | question_id = $qid , |
||
1966 | exercice_id = $new_id , |
||
1967 | question_order = ".$question_order; |
||
1968 | Database::query($sql); |
||
1969 | } |
||
1970 | } |
||
1971 | } |
||
1972 | } |
||
1973 | } |
||
1974 | |||
1975 | /** |
||
1976 | * Restore quiz-questions. |
||
1977 | * |
||
1978 | * @param int $id Question id |
||
1979 | * @param bool $idColumn Whether the 'id' column still exists in this table |
||
1980 | */ |
||
1981 | public function restore_quiz_question($id, $idColumn = true) |
||
1982 | { |
||
1983 | $em = Database::getManager(); |
||
1984 | $resources = $this->course->resources; |
||
1985 | /** @var QuizQuestion $question */ |
||
1986 | $question = isset($resources[RESOURCE_QUIZQUESTION][$id]) ? $resources[RESOURCE_QUIZQUESTION][$id] : null; |
||
1987 | $new_id = 0; |
||
1988 | |||
1989 | if (is_object($question)) { |
||
1990 | if ($question->is_restored()) { |
||
1991 | return $question->destination_id; |
||
1992 | } |
||
1993 | $table_que = Database::get_course_table(TABLE_QUIZ_QUESTION); |
||
1994 | $table_ans = Database::get_course_table(TABLE_QUIZ_ANSWER); |
||
1995 | $table_options = Database::get_course_table(TABLE_QUIZ_QUESTION_OPTION); |
||
1996 | |||
1997 | // check resources inside html from ckeditor tool and copy correct urls into recipient course |
||
1998 | $question->description = DocumentManager::replaceUrlWithNewCourseCode( |
||
1999 | $question->description, |
||
2000 | $this->course->code, |
||
2001 | $this->course->destination_path, |
||
2002 | $this->course->backup_path, |
||
2003 | $this->course->info['path'] |
||
2004 | ); |
||
2005 | |||
2006 | $imageNewId = ''; |
||
2007 | if (preg_match('/^quiz-.*$/', $question->picture) && |
||
2008 | isset($resources[RESOURCE_DOCUMENT]['image_quiz'][$question->picture]) |
||
2009 | ) { |
||
2010 | $imageNewId = $resources[RESOURCE_DOCUMENT]['image_quiz'][$question->picture]['destination_id']; |
||
2011 | } else { |
||
2012 | if (isset($resources[RESOURCE_DOCUMENT][$question->picture])) { |
||
2013 | $documentsToRestore = $resources[RESOURCE_DOCUMENT][$question->picture]; |
||
2014 | $imageNewId = $documentsToRestore->destination_id; |
||
2015 | } |
||
2016 | } |
||
2017 | $question->question = DocumentManager::replaceUrlWithNewCourseCode( |
||
2018 | $question->question, |
||
2019 | $this->course->code, |
||
2020 | $this->course->destination_path, |
||
2021 | $this->course->backup_path, |
||
2022 | $this->course->info['path'] |
||
2023 | ); |
||
2024 | $params = [ |
||
2025 | 'c_id' => $this->destination_course_id, |
||
2026 | 'question' => self::DBUTF8($question->question), |
||
2027 | 'description' => ($question->description === false ? '' : self::DBUTF8($question->description)), |
||
2028 | 'ponderation' => self::DBUTF8($question->ponderation), |
||
2029 | 'position' => self::DBUTF8($question->position), |
||
2030 | 'type' => self::DBUTF8($question->quiz_type), |
||
2031 | 'picture' => self::DBUTF8($imageNewId), |
||
2032 | 'level' => self::DBUTF8($question->level), |
||
2033 | 'extra' => self::DBUTF8($question->extra), |
||
2034 | ]; |
||
2035 | |||
2036 | $new_id = Database::insert($table_que, $params); |
||
2037 | |||
2038 | if ($new_id) { |
||
2039 | // If the ID column is still present, update it, otherwise just |
||
2040 | // continue |
||
2041 | if ($idColumn) { |
||
2042 | $sql = "UPDATE $table_que SET id = iid WHERE iid = $new_id"; |
||
2043 | Database::query($sql); |
||
2044 | } |
||
2045 | } else { |
||
2046 | // If no IID was generated, stop right there and return 0 |
||
2047 | return 0; |
||
2048 | } |
||
2049 | |||
2050 | $correctAnswers = []; |
||
2051 | $allAnswers = []; |
||
2052 | $onlyAnswers = []; |
||
2053 | |||
2054 | if (in_array($question->quiz_type, [DRAGGABLE, MATCHING, MATCHING_DRAGGABLE])) { |
||
2055 | $tempAnswerList = $question->answers; |
||
2056 | foreach ($tempAnswerList as &$value) { |
||
2057 | $value['answer'] = DocumentManager::replaceUrlWithNewCourseCode( |
||
2058 | $value['answer'], |
||
2059 | $this->course->code, |
||
2060 | $this->course->destination_path, |
||
2061 | $this->course->backup_path, |
||
2062 | $this->course->info['path'] |
||
2063 | ); |
||
2064 | } |
||
2065 | $allAnswers = array_column($tempAnswerList, 'answer', 'id'); |
||
2066 | } |
||
2067 | |||
2068 | if (in_array($question->quiz_type, [MATCHING, MATCHING_DRAGGABLE])) { |
||
2069 | $temp = []; |
||
2070 | foreach ($question->answers as $index => $answer) { |
||
2071 | $temp[$answer['position']] = $answer; |
||
2072 | } |
||
2073 | |||
2074 | foreach ($temp as $index => $answer) { |
||
2075 | // check resources inside html from ckeditor tool and copy correct urls into recipient course |
||
2076 | $answer['answer'] = DocumentManager::replaceUrlWithNewCourseCode( |
||
2077 | $answer['answer'], |
||
2078 | $this->course->code, |
||
2079 | $this->course->destination_path, |
||
2080 | $this->course->backup_path, |
||
2081 | $this->course->info['path'] |
||
2082 | ); |
||
2083 | |||
2084 | $answer['comment'] = DocumentManager::replaceUrlWithNewCourseCode( |
||
2085 | $answer['comment'], |
||
2086 | $this->course->code, |
||
2087 | $this->course->destination_path, |
||
2088 | $this->course->backup_path, |
||
2089 | $this->course->info['path'] |
||
2090 | ); |
||
2091 | |||
2092 | $quizAnswer = new CQuizAnswer(); |
||
2093 | $quizAnswer |
||
2094 | ->setCId($this->destination_course_id) |
||
2095 | ->setQuestionId($new_id) |
||
2096 | ->setAnswer(self::DBUTF8($answer['answer'])) |
||
2097 | ->setCorrect($answer['correct']) |
||
2098 | ->setComment($answer['comment'] === false ? '' : self::DBUTF8($answer['comment'])) |
||
2099 | ->setPonderation($answer['ponderation']) |
||
2100 | ->setPosition($answer['position']) |
||
2101 | ->setHotspotCoordinates($answer['hotspot_coordinates']) |
||
2102 | ->setHotspotType($answer['hotspot_type']) |
||
2103 | ->setIdAuto(0); |
||
2104 | |||
2105 | $em->persist($quizAnswer); |
||
2106 | $em->flush(); |
||
2107 | |||
2108 | $answerId = $quizAnswer->getId(); |
||
2109 | |||
2110 | if ($answerId) { |
||
2111 | $quizAnswer |
||
2112 | ->setId($answerId) |
||
2113 | ->setIdAuto($answerId); |
||
2114 | $em->merge($quizAnswer); |
||
2115 | $em->flush(); |
||
2116 | |||
2117 | $correctAnswers[$answerId] = $answer['correct']; |
||
2118 | $onlyAnswers[$answerId] = $answer['answer']; |
||
2119 | } |
||
2120 | } |
||
2121 | } else { |
||
2122 | foreach ($question->answers as $index => $answer) { |
||
2123 | // check resources inside html from ckeditor tool and copy correct urls into recipient course |
||
2124 | $answer['answer'] = DocumentManager::replaceUrlWithNewCourseCode( |
||
2125 | $answer['answer'], |
||
2126 | $this->course->code, |
||
2127 | $this->course->destination_path, |
||
2128 | $this->course->backup_path, |
||
2129 | $this->course->info['path'] |
||
2130 | ); |
||
2131 | |||
2132 | $answer['comment'] = DocumentManager::replaceUrlWithNewCourseCode( |
||
2133 | $answer['comment'], |
||
2134 | $this->course->code, |
||
2135 | $this->course->destination_path, |
||
2136 | $this->course->backup_path, |
||
2137 | $this->course->info['path'] |
||
2138 | ); |
||
2139 | |||
2140 | $params = [ |
||
2141 | 'c_id' => $this->destination_course_id, |
||
2142 | 'question_id' => $new_id, |
||
2143 | 'answer' => self::DBUTF8($answer['answer']), |
||
2144 | 'correct' => $answer['correct'], |
||
2145 | 'comment' => ($answer['comment'] === false ? '' : self::DBUTF8($answer['comment'])), |
||
2146 | 'ponderation' => $answer['ponderation'], |
||
2147 | 'position' => $answer['position'], |
||
2148 | 'hotspot_coordinates' => $answer['hotspot_coordinates'], |
||
2149 | 'hotspot_type' => $answer['hotspot_type'], |
||
2150 | 'id_auto' => 0, |
||
2151 | 'destination' => '', |
||
2152 | ]; |
||
2153 | |||
2154 | $answerId = Database::insert($table_ans, $params); |
||
2155 | |||
2156 | if ($answerId) { |
||
2157 | if ($idColumn) { |
||
2158 | $sql = "UPDATE $table_ans SET id = iid, id_auto = iid WHERE iid = $answerId"; |
||
2159 | Database::query($sql); |
||
2160 | } else { |
||
2161 | $sql = "UPDATE $table_ans SET id_auto = iid WHERE iid = $answerId"; |
||
2162 | Database::query($sql); |
||
2163 | } |
||
2164 | } |
||
2165 | |||
2166 | $correctAnswers[$answerId] = $answer['correct']; |
||
2167 | $onlyAnswers[$answerId] = $answer['answer']; |
||
2168 | } |
||
2169 | } |
||
2170 | |||
2171 | // Current course id |
||
2172 | $course_id = api_get_course_int_id(); |
||
2173 | |||
2174 | // Moving quiz_question_options |
||
2175 | if ($question->quiz_type == MULTIPLE_ANSWER_TRUE_FALSE) { |
||
2176 | if (count($question->question_options) < 3) { |
||
2177 | $options = [1 => 'True', 2 => 'False', 3 => 'DoubtScore']; |
||
2178 | $correct = []; |
||
2179 | for ($i = 1; $i <= 3; $i++) { |
||
2180 | $lastId = Question::saveQuestionOption( |
||
2181 | $new_id, |
||
2182 | $options[$i], |
||
2183 | $this->destination_course_id, |
||
2184 | $i |
||
2185 | ); |
||
2186 | $correct[$i] = $lastId; |
||
2187 | } |
||
2188 | |||
2189 | $correctAnswerValues = Database::select( |
||
2190 | 'DISTINCT(correct)', |
||
2191 | $table_ans, |
||
2192 | [ |
||
2193 | 'WHERE' => [ |
||
2194 | 'question_id = ? AND c_id = ? ' => [ |
||
2195 | $new_id, |
||
2196 | $this->destination_course_id, |
||
2197 | ], |
||
2198 | ], |
||
2199 | 'ORDER' => 'correct ASC', |
||
2200 | ] |
||
2201 | ); |
||
2202 | $i = 1; |
||
2203 | foreach ($correctAnswerValues as $correctAnswer) { |
||
2204 | $params = []; |
||
2205 | $params['correct'] = $correct[$i]; |
||
2206 | Database::update( |
||
2207 | $table_ans, |
||
2208 | $params, |
||
2209 | [ |
||
2210 | 'question_id = ? AND c_id = ? AND correct = ? ' => [ |
||
2211 | $new_id, |
||
2212 | $this->destination_course_id, |
||
2213 | $correctAnswer['correct'], |
||
2214 | ], |
||
2215 | ], |
||
2216 | false |
||
2217 | ); |
||
2218 | $i++; |
||
2219 | } |
||
2220 | } else { |
||
2221 | $question_option_list = Question::readQuestionOption($id, $course_id); |
||
2222 | |||
2223 | // Question copied from the current platform |
||
2224 | if ($question_option_list) { |
||
2225 | $old_option_ids = []; |
||
2226 | foreach ($question_option_list as $item) { |
||
2227 | if (isset($item['iid'])) { |
||
2228 | $old_id = $item['iid']; |
||
2229 | unset($item['iid']); |
||
2230 | unset($item['id']); |
||
2231 | } else { |
||
2232 | $old_id = $item['id']; |
||
2233 | unset($item['id']); |
||
2234 | } |
||
2235 | $item['question_id'] = $new_id; |
||
2236 | $item['c_id'] = $this->destination_course_id; |
||
2237 | $question_option_id = Database::insert($table_options, $item); |
||
2238 | if ($question_option_id && $idColumn) { |
||
2239 | $old_option_ids[$old_id] = $question_option_id; |
||
2240 | $sql = "UPDATE $table_options SET id = iid WHERE iid = $question_option_id"; |
||
2241 | Database::query($sql); |
||
2242 | } |
||
2243 | } |
||
2244 | if ($old_option_ids) { |
||
2245 | $new_answers = Database::select( |
||
2246 | 'iid, correct', |
||
2247 | $table_ans, |
||
2248 | [ |
||
2249 | 'WHERE' => [ |
||
2250 | 'question_id = ? AND c_id = ? ' => [ |
||
2251 | $new_id, |
||
2252 | $this->destination_course_id, |
||
2253 | ], |
||
2254 | ], |
||
2255 | ] |
||
2256 | ); |
||
2257 | |||
2258 | foreach ($new_answers as $answer_item) { |
||
2259 | $params = []; |
||
2260 | $params['correct'] = $old_option_ids[$answer_item['correct']]; |
||
2261 | Database::update( |
||
2262 | $table_ans, |
||
2263 | $params, |
||
2264 | [ |
||
2265 | 'iid = ? AND c_id = ? AND question_id = ? ' => [ |
||
2266 | $answer_item['iid'], |
||
2267 | $this->destination_course_id, |
||
2268 | $new_id, |
||
2269 | ], |
||
2270 | ], |
||
2271 | false |
||
2272 | ); |
||
2273 | } |
||
2274 | } |
||
2275 | } else { |
||
2276 | $new_options = []; |
||
2277 | if (isset($question->question_options)) { |
||
2278 | foreach ($question->question_options as $obj) { |
||
2279 | $item = []; |
||
2280 | $item['question_id'] = $new_id; |
||
2281 | $item['c_id'] = $this->destination_course_id; |
||
2282 | $item['name'] = $obj->obj->name; |
||
2283 | $item['position'] = $obj->obj->position; |
||
2284 | $question_option_id = Database::insert($table_options, $item); |
||
2285 | |||
2286 | if ($question_option_id) { |
||
2287 | $new_options[$obj->obj->id] = $question_option_id; |
||
2288 | $sql = "UPDATE $table_options SET id = iid WHERE iid = $question_option_id"; |
||
2289 | Database::query($sql); |
||
2290 | } |
||
2291 | } |
||
2292 | |||
2293 | foreach ($correctAnswers as $answer_id => $correct_answer) { |
||
2294 | $params = []; |
||
2295 | $params['correct'] = isset($new_options[$correct_answer]) ? $new_options[$correct_answer] : ''; |
||
2296 | Database::update( |
||
2297 | $table_ans, |
||
2298 | $params, |
||
2299 | [ |
||
2300 | 'iid = ? AND c_id = ? AND question_id = ? ' => [ |
||
2301 | $answer_id, |
||
2302 | $this->destination_course_id, |
||
2303 | $new_id, |
||
2304 | ], |
||
2305 | ], |
||
2306 | false |
||
2307 | ); |
||
2308 | } |
||
2309 | } |
||
2310 | } |
||
2311 | } |
||
2312 | } |
||
2313 | |||
2314 | // Fix correct answers |
||
2315 | if (in_array($question->quiz_type, [DRAGGABLE, MATCHING, MATCHING_DRAGGABLE])) { |
||
2316 | foreach ($correctAnswers as $answer_id => $correct_answer) { |
||
2317 | $params = []; |
||
2318 | |||
2319 | if (isset($allAnswers[$correct_answer])) { |
||
2320 | $correct = ''; |
||
2321 | foreach ($onlyAnswers as $key => $value) { |
||
2322 | if ($value == $allAnswers[$correct_answer]) { |
||
2323 | $correct = $key; |
||
2324 | break; |
||
2325 | } |
||
2326 | } |
||
2327 | |||
2328 | $params['correct'] = $correct; |
||
2329 | Database::update( |
||
2330 | $table_ans, |
||
2331 | $params, |
||
2332 | [ |
||
2333 | 'iid = ? AND c_id = ? AND question_id = ? ' => [ |
||
2334 | $answer_id, |
||
2335 | $this->destination_course_id, |
||
2336 | $new_id, |
||
2337 | ], |
||
2338 | ] |
||
2339 | ); |
||
2340 | } |
||
2341 | } |
||
2342 | } |
||
2343 | |||
2344 | $this->course->resources[RESOURCE_QUIZQUESTION][$id]->destination_id = $new_id; |
||
2345 | } |
||
2346 | |||
2347 | return $new_id; |
||
2348 | } |
||
2349 | |||
2350 | /** |
||
2351 | * @todo : add session id when used for session |
||
2352 | */ |
||
2353 | public function restore_test_category($session_id, $respect_base_content, $destination_course_code) |
||
2354 | { |
||
2355 | // Cannot restore a test category to a session. |
||
2356 | if (!empty($session_id)) { |
||
2357 | return false; |
||
2358 | } |
||
2359 | |||
2360 | $destinationCourseId = $this->destination_course_info['real_id']; |
||
2361 | // Let's restore the categories |
||
2362 | $categoryOldVsNewList = []; // used to build the quiz_question_rel_category table |
||
2363 | if ($this->course->has_resources(RESOURCE_TEST_CATEGORY)) { |
||
2364 | $resources = $this->course->resources; |
||
2365 | foreach ($resources[RESOURCE_TEST_CATEGORY] as $id => $courseCopyTestCategory) { |
||
2366 | $categoryOldVsNewList[$courseCopyTestCategory->source_id] = $id; |
||
2367 | // check if this test_category already exist in the destination BDD |
||
2368 | // do not Database::escape_string $title and $description, it will be done later |
||
2369 | $title = $courseCopyTestCategory->title; |
||
2370 | $description = $courseCopyTestCategory->description; |
||
2371 | if (TestCategory::categoryTitleExists($title, $destinationCourseId)) { |
||
2372 | switch ($this->file_option) { |
||
2373 | case FILE_SKIP: |
||
2374 | //Do nothing |
||
2375 | break; |
||
2376 | case FILE_RENAME: |
||
2377 | $new_title = $title.'_'; |
||
2378 | while (TestCategory::categoryTitleExists($new_title, $destinationCourseId)) { |
||
2379 | $new_title .= '_'; |
||
2380 | } |
||
2381 | $test_category = new TestCategory(); |
||
2382 | $test_category->name = $new_title; |
||
2383 | $test_category->description = $description; |
||
2384 | $new_id = $test_category->save($destinationCourseId); |
||
2385 | $categoryOldVsNewList[$courseCopyTestCategory->source_id] = $new_id; |
||
2386 | break; |
||
2387 | case FILE_OVERWRITE: |
||
2388 | // get category from source |
||
2389 | $destinationCategoryId = TestCategory::get_category_id_for_title( |
||
2390 | $title, |
||
2391 | $destinationCourseId |
||
2392 | ); |
||
2393 | if ($destinationCategoryId) { |
||
2394 | $my_cat = new TestCategory(); |
||
2395 | $my_cat = $my_cat->getCategory($destinationCategoryId, $destinationCourseId); |
||
2396 | $my_cat->name = $title; |
||
2397 | $my_cat->description = $description; |
||
2398 | $my_cat->modifyCategory($destinationCourseId); |
||
2399 | $categoryOldVsNewList[$courseCopyTestCategory->source_id] = $destinationCategoryId; |
||
2400 | } |
||
2401 | break; |
||
2402 | } |
||
2403 | } else { |
||
2404 | // create a new test_category |
||
2405 | $test_category = new TestCategory(); |
||
2406 | $test_category->name = $title; |
||
2407 | $test_category->description = $description; |
||
2408 | $new_id = $test_category->save($destinationCourseId); |
||
2409 | $categoryOldVsNewList[$courseCopyTestCategory->source_id] = $new_id; |
||
2410 | } |
||
2411 | $this->course->resources[RESOURCE_TEST_CATEGORY][$id]->destination_id = $categoryOldVsNewList[$courseCopyTestCategory->source_id]; |
||
2412 | } |
||
2413 | } |
||
2414 | |||
2415 | // lets check if quizzes-question are restored too, |
||
2416 | // to redo the link between test_category and quizzes question for questions restored |
||
2417 | // we can use the source_id field |
||
2418 | // question source_id => category source_id |
||
2419 | if ($this->course->has_resources(RESOURCE_QUIZQUESTION)) { |
||
2420 | // check the category number of each question restored |
||
2421 | if (!empty($resources[RESOURCE_QUIZQUESTION])) { |
||
2422 | foreach ($resources[RESOURCE_QUIZQUESTION] as $id => $courseCopyQuestion) { |
||
2423 | $newQuestionId = $resources[RESOURCE_QUIZQUESTION][$id]->destination_id; |
||
2424 | $questionCategoryId = $courseCopyQuestion->question_category; |
||
2425 | if ($newQuestionId > 0 && |
||
2426 | $questionCategoryId > 0 && |
||
2427 | isset($categoryOldVsNewList[$questionCategoryId]) |
||
2428 | ) { |
||
2429 | TestCategory::addCategoryToQuestion( |
||
2430 | $categoryOldVsNewList[$questionCategoryId], |
||
2431 | $newQuestionId, |
||
2432 | $destinationCourseId |
||
2433 | ); |
||
2434 | } |
||
2435 | } |
||
2436 | } |
||
2437 | } |
||
2438 | } |
||
2439 | |||
2440 | /** |
||
2441 | * Restore surveys. |
||
2442 | * |
||
2443 | * @param int $sessionId Optional. The session id |
||
2444 | */ |
||
2445 | public function restore_surveys($sessionId = 0) |
||
2621 | } |
||
2622 | } |
||
2623 | } |
||
2624 | } |
||
2625 | } |
||
2626 | } |
||
2627 | |||
2628 | /** |
||
2629 | * Check availability of a survey code. |
||
2630 | * |
||
2631 | * @param string $survey_code |
||
2632 | * |
||
2633 | * @return bool |
||
2634 | */ |
||
2635 | public function is_survey_code_available($survey_code) |
||
2636 | { |
||
2637 | $table_sur = Database::get_course_table(TABLE_SURVEY); |
||
2638 | $sql = "SELECT * FROM $table_sur |
||
2639 | WHERE |
||
2640 | c_id = ".$this->destination_course_id." AND |
||
2641 | code = '".self::DBUTF8escapestring($survey_code)."'"; |
||
2642 | $result = Database::query($sql); |
||
2643 | if (Database::num_rows($result) > 0) { |
||
2644 | return false; |
||
2645 | } else { |
||
2646 | return true; |
||
2647 | } |
||
2648 | } |
||
2649 | |||
2650 | /** |
||
2651 | * Restore survey-questions. |
||
2652 | * |
||
2653 | * @param int $id |
||
2654 | * @param string $survey_id |
||
2655 | */ |
||
2656 | public function restore_survey_question($id, $survey_id) |
||
2657 | { |
||
2658 | $resources = $this->course->resources; |
||
2659 | $question = $resources[RESOURCE_SURVEYQUESTION][$id]; |
||
2660 | $new_id = 0; |
||
2661 | |||
2662 | if (is_object($question)) { |
||
2663 | if ($question->is_restored()) { |
||
2664 | return $question->destination_id; |
||
2665 | } |
||
2666 | $table_que = Database::get_course_table(TABLE_SURVEY_QUESTION); |
||
2667 | $table_ans = Database::get_course_table(TABLE_SURVEY_QUESTION_OPTION); |
||
2668 | |||
2669 | // check resources inside html from ckeditor tool and copy correct urls into recipient course |
||
2670 | $question->survey_question = DocumentManager::replaceUrlWithNewCourseCode( |
||
2671 | $question->survey_question, |
||
2672 | $this->course->code, |
||
2673 | $this->course->destination_path, |
||
2674 | $this->course->backup_path, |
||
2675 | $this->course->info['path'] |
||
2676 | ); |
||
2677 | |||
2678 | $params = [ |
||
2679 | 'c_id' => $this->destination_course_id, |
||
2680 | 'survey_id' => self::DBUTF8($survey_id), |
||
2681 | 'survey_question' => ($question->survey_question === false ? '' : self::DBUTF8($question->survey_question)), |
||
2682 | 'survey_question_comment' => self::DBUTF8($question->survey_question_comment), |
||
2683 | 'type' => self::DBUTF8($question->survey_question_type), |
||
2684 | 'display' => self::DBUTF8($question->display), |
||
2685 | 'sort' => self::DBUTF8($question->sort), |
||
2686 | 'shared_question_id' => self::DBUTF8($question->shared_question_id), |
||
2687 | 'max_value' => self::DBUTF8($question->max_value), |
||
2688 | ]; |
||
2689 | if (api_get_configuration_value('allow_required_survey_questions')) { |
||
2690 | if (isset($question->is_required)) { |
||
2691 | $params['is_required'] = $question->is_required; |
||
2692 | } |
||
2693 | } |
||
2694 | |||
2695 | $new_id = Database::insert($table_que, $params); |
||
2696 | if ($new_id) { |
||
2697 | $sql = "UPDATE $table_que SET question_id = iid WHERE iid = $new_id"; |
||
2698 | Database::query($sql); |
||
2699 | |||
2700 | foreach ($question->answers as $index => $answer) { |
||
2701 | // check resources inside html from ckeditor tool and copy correct urls into recipient course |
||
2702 | $answer['option_text'] = DocumentManager::replaceUrlWithNewCourseCode( |
||
2703 | $answer['option_text'], |
||
2704 | $this->course->code, |
||
2705 | $this->course->destination_path, |
||
2706 | $this->course->backup_path, |
||
2707 | $this->course->info['path'] |
||
2708 | ); |
||
2709 | |||
2710 | $params = [ |
||
2711 | 'c_id' => $this->destination_course_id, |
||
2712 | 'question_id' => $new_id, |
||
2713 | 'option_text' => ($answer['option_text'] === false ? '' : self::DBUTF8($answer['option_text'])), |
||
2714 | 'sort' => $answer['sort'], |
||
2715 | 'survey_id' => self::DBUTF8($survey_id), |
||
2716 | ]; |
||
2717 | $answerId = Database::insert($table_ans, $params); |
||
2718 | if ($answerId) { |
||
2719 | $sql = "UPDATE $table_ans SET question_option_id = iid |
||
2720 | WHERE iid = $answerId"; |
||
2721 | Database::query($sql); |
||
2722 | } |
||
2723 | } |
||
2724 | $this->course->resources[RESOURCE_SURVEYQUESTION][$id]->destination_id = $new_id; |
||
2725 | } |
||
2726 | } |
||
2727 | |||
2728 | return $new_id; |
||
2729 | } |
||
2730 | |||
2731 | /** |
||
2732 | * @param int $sessionId |
||
2733 | * @param bool $baseContent |
||
2734 | */ |
||
2735 | public function restore_learnpath_category($sessionId = 0, $baseContent = false) |
||
2736 | { |
||
2737 | $reuseExisting = false; |
||
2738 | |||
2739 | if (isset($this->tool_copy_settings['learnpath_category']) && |
||
2740 | isset($this->tool_copy_settings['learnpath_category']['reuse_existing']) && |
||
2741 | true === $this->tool_copy_settings['learnpath_category']['reuse_existing'] |
||
2742 | ) { |
||
2743 | $reuseExisting = true; |
||
2744 | } |
||
2745 | |||
2746 | $tblLpCategory = Database::get_course_table(TABLE_LP_CATEGORY); |
||
2747 | |||
2748 | if ($this->course->has_resources(RESOURCE_LEARNPATH_CATEGORY)) { |
||
2749 | $resources = $this->course->resources; |
||
2750 | /** @var LearnPathCategory $item */ |
||
2751 | foreach ($resources[RESOURCE_LEARNPATH_CATEGORY] as $id => $item) { |
||
2752 | /** @var CLpCategory $lpCategory */ |
||
2753 | $lpCategory = $item->object; |
||
2754 | |||
2755 | if ($lpCategory) { |
||
2756 | $existingLpCategory = Database::select( |
||
2757 | 'iid', |
||
2758 | $tblLpCategory, |
||
2759 | [ |
||
2760 | 'WHERE' => [ |
||
2761 | 'c_id = ? AND name = ?' => [$this->destination_course_id, $lpCategory->getName()], |
||
2762 | ], |
||
2763 | ], |
||
2764 | 'first' |
||
2765 | ); |
||
2766 | |||
2767 | if ($reuseExisting && !empty($existingLpCategory)) { |
||
2768 | $categoryId = $existingLpCategory['iid']; |
||
2769 | } else { |
||
2770 | $values = [ |
||
2771 | 'c_id' => $this->destination_course_id, |
||
2772 | 'name' => $lpCategory->getName(), |
||
2773 | ]; |
||
2774 | $categoryId = \learnpath::createCategory($values); |
||
2775 | } |
||
2776 | |||
2777 | if ($categoryId) { |
||
2778 | $this->course->resources[RESOURCE_LEARNPATH_CATEGORY][$id]->destination_id = $categoryId; |
||
2779 | } |
||
2780 | } |
||
2781 | } |
||
2782 | } |
||
2783 | } |
||
2784 | |||
2785 | /** |
||
2786 | * Restoring learning paths. |
||
2787 | * |
||
2788 | * @param int $session_id |
||
2789 | * @param bool|false $respect_base_content |
||
2790 | */ |
||
2791 | public function restore_learnpaths($session_id = 0, $respect_base_content = false) |
||
2792 | { |
||
2793 | $session_id = (int) $session_id; |
||
2794 | if ($this->course->has_resources(RESOURCE_LEARNPATH)) { |
||
2795 | $table_main = Database::get_course_table(TABLE_LP_MAIN); |
||
2796 | $table_item = Database::get_course_table(TABLE_LP_ITEM); |
||
2797 | $table_tool = Database::get_course_table(TABLE_TOOL_LIST); |
||
2798 | |||
2799 | $resources = $this->course->resources; |
||
2800 | $origin_path = $this->course->backup_path.'/upload/learning_path/images/'; |
||
2801 | $destination_path = api_get_path(SYS_COURSE_PATH). |
||
2802 | $this->course->destination_path.'/upload/learning_path/images/'; |
||
2803 | |||
2804 | // Choose default visibility |
||
2805 | $toolVisibility = api_get_setting('tool_visible_by_default_at_creation'); |
||
2806 | $defaultLpVisibility = 'invisible'; |
||
2807 | if (isset($toolVisibility['learning_path']) && $toolVisibility['learning_path'] == 'true') { |
||
2808 | $defaultLpVisibility = 'visible'; |
||
2809 | } |
||
2810 | |||
2811 | foreach ($resources[RESOURCE_LEARNPATH] as $id => $lp) { |
||
2812 | $condition_session = ''; |
||
2813 | if (!empty($session_id)) { |
||
2814 | if ($respect_base_content) { |
||
2815 | $my_session_id = $lp->session_id; |
||
2816 | if (!empty($lp->session_id)) { |
||
2817 | $my_session_id = $session_id; |
||
2818 | } |
||
2819 | $condition_session = $my_session_id; |
||
2820 | } else { |
||
2821 | $session_id = (int) $session_id; |
||
2822 | $condition_session = $session_id; |
||
2823 | } |
||
2824 | } |
||
2825 | |||
2826 | // Adding the LP image |
||
2827 | if (!empty($lp->preview_image)) { |
||
2828 | $new_filename = uniqid('').substr( |
||
2829 | $lp->preview_image, |
||
2830 | strlen($lp->preview_image) - 7, |
||
2831 | strlen($lp->preview_image) |
||
2832 | ); |
||
2833 | |||
2834 | if (file_exists($origin_path.$lp->preview_image) && |
||
2835 | !is_dir($origin_path.$lp->preview_image) |
||
2836 | ) { |
||
2837 | $copy_result = copy( |
||
2838 | $origin_path.$lp->preview_image, |
||
2839 | $destination_path.$new_filename |
||
2840 | ); |
||
2841 | if ($copy_result) { |
||
2842 | $lp->preview_image = $new_filename; |
||
2843 | // Create 64 version from original |
||
2844 | $temp = new \Image($destination_path.$new_filename); |
||
2845 | $temp->resize(64); |
||
2846 | $pathInfo = pathinfo($new_filename); |
||
2847 | if ($pathInfo) { |
||
2848 | $filename = $pathInfo['filename']; |
||
2849 | $extension = $pathInfo['extension']; |
||
2850 | $temp->send_image($destination_path.'/'.$filename.'.64.'.$extension); |
||
2851 | } |
||
2852 | } else { |
||
2853 | $lp->preview_image = ''; |
||
2854 | } |
||
2855 | } |
||
2856 | } |
||
2857 | |||
2858 | if ($this->add_text_in_items) { |
||
2859 | $lp->name = $lp->name.' '.get_lang('CopyLabelSuffix'); |
||
2860 | } |
||
2861 | |||
2862 | if (isset($this->tool_copy_settings['learnpaths'])) { |
||
2863 | if (isset($this->tool_copy_settings['learnpaths']['reset_dates']) && |
||
2864 | $this->tool_copy_settings['learnpaths']['reset_dates'] |
||
2865 | ) { |
||
2866 | $lp->created_on = api_get_utc_datetime(); |
||
2867 | $lp->modified_on = api_get_utc_datetime(); |
||
2868 | $lp->publicated_on = null; |
||
2869 | } |
||
2870 | } |
||
2871 | |||
2872 | $lp->expired_on = isset($lp->expired_on) && $lp->expired_on === '0000-00-00 00:00:00' ? null : $lp->expired_on; |
||
2873 | $lp->publicated_on = isset($lp->publicated_on) && $lp->publicated_on === '0000-00-00 00:00:00' ? null : $lp->publicated_on; |
||
2874 | |||
2875 | if (isset($lp->categoryId)) { |
||
2876 | $lp->categoryId = (int) $lp->categoryId; |
||
2877 | } |
||
2878 | |||
2879 | $categoryId = 0; |
||
2880 | if (!empty($lp->categoryId)) { |
||
2881 | if (isset($resources[RESOURCE_LEARNPATH_CATEGORY][$lp->categoryId])) { |
||
2882 | $categoryId = $resources[RESOURCE_LEARNPATH_CATEGORY][$lp->categoryId]->destination_id; |
||
2883 | } |
||
2884 | } |
||
2885 | $params = [ |
||
2886 | 'c_id' => $this->destination_course_id, |
||
2887 | 'lp_type' => $lp->lp_type, |
||
2888 | 'name' => self::DBUTF8($lp->name), |
||
2889 | 'path' => self::DBUTF8($lp->path), |
||
2890 | 'ref' => $lp->ref, |
||
2891 | 'description' => self::DBUTF8($lp->description), |
||
2892 | 'content_local' => self::DBUTF8($lp->content_local), |
||
2893 | 'default_encoding' => self::DBUTF8($lp->default_encoding), |
||
2894 | 'default_view_mod' => self::DBUTF8($lp->default_view_mod), |
||
2895 | 'prevent_reinit' => self::DBUTF8($lp->prevent_reinit), |
||
2896 | 'force_commit' => self::DBUTF8($lp->force_commit), |
||
2897 | 'content_maker' => self::DBUTF8($lp->content_maker), |
||
2898 | 'display_order' => self::DBUTF8($lp->display_order), |
||
2899 | 'js_lib' => self::DBUTF8($lp->js_lib), |
||
2900 | 'content_license' => self::DBUTF8($lp->content_license), |
||
2901 | 'author' => self::DBUTF8($lp->author), |
||
2902 | 'preview_image' => self::DBUTF8($lp->preview_image), |
||
2903 | 'use_max_score' => self::DBUTF8($lp->use_max_score), |
||
2904 | 'autolaunch' => self::DBUTF8(isset($lp->autolaunch) ? $lp->autolaunch : ''), |
||
2905 | 'created_on' => empty($lp->created_on) ? api_get_utc_datetime() : self::DBUTF8($lp->created_on), |
||
2906 | 'modified_on' => empty($lp->modified_on) ? api_get_utc_datetime() : self::DBUTF8($lp->modified_on), |
||
2907 | 'publicated_on' => empty($lp->publicated_on) ? api_get_utc_datetime() : self::DBUTF8($lp->publicated_on), |
||
2908 | 'expired_on' => self::DBUTF8($lp->expired_on), |
||
2909 | 'debug' => self::DBUTF8($lp->debug), |
||
2910 | 'theme' => '', |
||
2911 | 'session_id' => $session_id, |
||
2912 | 'prerequisite' => 0, |
||
2913 | 'hide_toc_frame' => self::DBUTF8(isset($lp->hideTableOfContents) ? $lp->hideTableOfContents : 0), |
||
2914 | 'subscribe_users' => self::DBUTF8(isset($lp->subscribeUsers) ? $lp->subscribeUsers : 0), |
||
2915 | 'seriousgame_mode' => 0, |
||
2916 | 'category_id' => $categoryId, |
||
2917 | 'max_attempts' => 0, |
||
2918 | ]; |
||
2919 | |||
2920 | if (api_get_configuration_value('lp_minimum_time')) { |
||
2921 | if (isset($lp->accumulateWorkTime) && !empty($lp->accumulateWorkTime)) { |
||
2922 | $params['accumulate_work_time'] = $lp->accumulateWorkTime; |
||
2923 | } |
||
2924 | } |
||
2925 | |||
2926 | if (!empty($condition_session)) { |
||
2927 | $params['session_id'] = $condition_session; |
||
2928 | } |
||
2929 | |||
2930 | $new_lp_id = Database::insert($table_main, $params); |
||
2931 | |||
2932 | if ($new_lp_id) { |
||
2933 | // The following only makes sense if a new LP was |
||
2934 | // created in the destination course |
||
2935 | $sql = "UPDATE $table_main SET id = iid WHERE iid = $new_lp_id"; |
||
2936 | Database::query($sql); |
||
2937 | |||
2938 | if ($lp->visibility) { |
||
2939 | $params = [ |
||
2940 | 'c_id' => $this->destination_course_id, |
||
2941 | 'name' => self::DBUTF8($lp->name), |
||
2942 | 'link' => "lp/lp_controller.php?action=view&lp_id=$new_lp_id&id_session=$session_id", |
||
2943 | 'image' => 'scormbuilder.gif', |
||
2944 | 'visibility' => '0', |
||
2945 | 'admin' => '0', |
||
2946 | 'address' => 'squaregrey.gif', |
||
2947 | 'session_id' => $session_id, |
||
2948 | ]; |
||
2949 | $insertId = Database::insert($table_tool, $params); |
||
2950 | if ($insertId) { |
||
2951 | $sql = "UPDATE $table_tool SET id = iid WHERE iid = $insertId"; |
||
2952 | Database::query($sql); |
||
2953 | } |
||
2954 | } |
||
2955 | |||
2956 | if (isset($lp->extraFields) && !empty($lp->extraFields)) { |
||
2957 | $extraFieldValue = new \ExtraFieldValue('lp'); |
||
2958 | foreach ($lp->extraFields as $extraField) { |
||
2959 | $params = [ |
||
2960 | 'item_id' => $new_lp_id, |
||
2961 | 'value' => $extraField['value'], |
||
2962 | 'variable' => $extraField['variable'], |
||
2963 | ]; |
||
2964 | $extraFieldValue->save($params); |
||
2965 | } |
||
2966 | } |
||
2967 | |||
2968 | api_item_property_update( |
||
2969 | $this->destination_course_info, |
||
2970 | TOOL_LEARNPATH, |
||
2971 | $new_lp_id, |
||
2972 | 'LearnpathAdded', |
||
2973 | api_get_user_id(), |
||
2974 | 0, |
||
2975 | 0, |
||
2976 | 0, |
||
2977 | 0, |
||
2978 | $session_id |
||
2979 | ); |
||
2980 | |||
2981 | // Set the new LP to visible |
||
2982 | api_item_property_update( |
||
2983 | $this->destination_course_info, |
||
2984 | TOOL_LEARNPATH, |
||
2985 | $new_lp_id, |
||
2986 | $defaultLpVisibility, |
||
2987 | api_get_user_id(), |
||
2988 | 0, |
||
2989 | 0, |
||
2990 | 0, |
||
2991 | 0, |
||
2992 | $session_id |
||
2993 | ); |
||
2994 | |||
2995 | $new_item_ids = []; |
||
2996 | $parent_item_ids = []; |
||
2997 | $previous_item_ids = []; |
||
2998 | $next_item_ids = []; |
||
2999 | $old_prerequisite = []; |
||
3000 | $old_refs = []; |
||
3001 | $prerequisite_ids = []; |
||
3002 | |||
3003 | foreach ($lp->get_items() as $index => $item) { |
||
3004 | // we set the ref code here and then we update in a for loop |
||
3005 | $ref = $item['ref']; |
||
3006 | |||
3007 | // Dealing with path the same way as ref as some data has |
||
3008 | // been put into path when it's a local resource |
||
3009 | // Only fix the path for no scos |
||
3010 | if ($item['item_type'] === 'sco') { |
||
3011 | $path = $item['path']; |
||
3012 | } else { |
||
3013 | $path = $this->get_new_id($item['item_type'], $item['path']); |
||
3014 | } |
||
3015 | |||
3016 | $item['item_type'] = $item['item_type'] === 'dokeos_chapter' ? 'dir' : $item['item_type']; |
||
3017 | |||
3018 | $masteryScore = $item['mastery_score']; |
||
3019 | // If item is a chamilo quiz, then use the max score as mastery_score. |
||
3020 | if ($item['item_type'] === 'quiz') { |
||
3021 | if (empty($masteryScore)) { |
||
3022 | $masteryScore = $item['max_score']; |
||
3023 | } |
||
3024 | } |
||
3025 | |||
3026 | $prerequisiteMinScore = $item['prerequisite_min_score'] ?? null; |
||
3027 | $prerequisiteMaxScore = $item['prerequisite_max_score'] ?? null; |
||
3028 | |||
3029 | $params = [ |
||
3030 | 'c_id' => $this->destination_course_id, |
||
3031 | 'lp_id' => self::DBUTF8($new_lp_id), |
||
3032 | 'item_type' => self::DBUTF8($item['item_type']), |
||
3033 | 'ref' => self::DBUTF8($ref), |
||
3034 | 'path' => self::DBUTF8($path), |
||
3035 | 'title' => self::DBUTF8($item['title']), |
||
3036 | 'description' => self::DBUTF8($item['description']), |
||
3037 | 'min_score' => self::DBUTF8($item['min_score']), |
||
3038 | 'max_score' => self::DBUTF8($item['max_score']), |
||
3039 | 'mastery_score' => self::DBUTF8($masteryScore), |
||
3040 | 'prerequisite_min_score' => $prerequisiteMinScore, |
||
3041 | 'prerequisite_max_score' => $prerequisiteMaxScore, |
||
3042 | 'parent_item_id' => self::DBUTF8($item['parent_item_id']), |
||
3043 | 'previous_item_id' => self::DBUTF8($item['previous_item_id']), |
||
3044 | 'next_item_id' => self::DBUTF8($item['next_item_id']), |
||
3045 | 'display_order' => self::DBUTF8($item['display_order']), |
||
3046 | 'prerequisite' => self::DBUTF8($item['prerequisite']), |
||
3047 | 'parameters' => self::DBUTF8($item['parameters']), |
||
3048 | 'audio' => self::DBUTF8($item['audio']), |
||
3049 | 'launch_data' => self::DBUTF8($item['launch_data']), |
||
3050 | ]; |
||
3051 | |||
3052 | $new_item_id = Database::insert($table_item, $params); |
||
3053 | if ($new_item_id) { |
||
3054 | $sql = "UPDATE $table_item SET id = iid WHERE iid = $new_item_id"; |
||
3055 | Database::query($sql); |
||
3056 | |||
3057 | //save a link between old and new item IDs |
||
3058 | $new_item_ids[$item['id']] = $new_item_id; |
||
3059 | //save a reference of items that need a parent_item_id refresh |
||
3060 | $parent_item_ids[$new_item_id] = $item['parent_item_id']; |
||
3061 | //save a reference of items that need a previous_item_id refresh |
||
3062 | $previous_item_ids[$new_item_id] = $item['previous_item_id']; |
||
3063 | //save a reference of items that need a next_item_id refresh |
||
3064 | $next_item_ids[$new_item_id] = $item['next_item_id']; |
||
3065 | |||
3066 | if (!empty($item['prerequisite'])) { |
||
3067 | if ($lp->lp_type == '2') { |
||
3068 | // if is an sco |
||
3069 | $old_prerequisite[$new_item_id] = $item['prerequisite']; |
||
3070 | } else { |
||
3071 | $old_prerequisite[$new_item_id] = isset($new_item_ids[$item['prerequisite']]) ? $new_item_ids[$item['prerequisite']] : ''; |
||
3072 | } |
||
3073 | } |
||
3074 | |||
3075 | if (!empty($ref)) { |
||
3076 | if ($lp->lp_type == '2') { |
||
3077 | // if is an sco |
||
3078 | $old_refs[$new_item_id] = $ref; |
||
3079 | } elseif (isset($new_item_ids[$ref])) { |
||
3080 | $old_refs[$new_item_id] = $new_item_ids[$ref]; |
||
3081 | } |
||
3082 | } |
||
3083 | $prerequisite_ids[$new_item_id] = $item['prerequisite']; |
||
3084 | } |
||
3085 | } |
||
3086 | |||
3087 | // Updating prerequisites |
||
3088 | foreach ($old_prerequisite as $key => $my_old_prerequisite) { |
||
3089 | if ($my_old_prerequisite != '') { |
||
3090 | $my_old_prerequisite = Database::escape_string($my_old_prerequisite); |
||
3091 | $sql = "UPDATE $table_item SET prerequisite = '$my_old_prerequisite' |
||
3092 | WHERE c_id = ".$this->destination_course_id." AND id = '".$key."' "; |
||
3093 | Database::query($sql); |
||
3094 | } |
||
3095 | } |
||
3096 | |||
3097 | // Updating refs |
||
3098 | foreach ($old_refs as $key => $my_old_ref) { |
||
3099 | if ($my_old_ref != '') { |
||
3100 | $my_old_ref = Database::escape_string($my_old_ref); |
||
3101 | $sql = "UPDATE $table_item SET ref = '$my_old_ref' |
||
3102 | WHERE c_id = ".$this->destination_course_id." AND id = $key"; |
||
3103 | Database::query($sql); |
||
3104 | } |
||
3105 | } |
||
3106 | |||
3107 | foreach ($parent_item_ids as $new_item_id => $parent_item_old_id) { |
||
3108 | $new_item_id = (int) $new_item_id; |
||
3109 | $parent_new_id = 0; |
||
3110 | if ($parent_item_old_id != 0) { |
||
3111 | $parent_new_id = isset($new_item_ids[$parent_item_old_id]) ? $new_item_ids[$parent_item_old_id] : 0; |
||
3112 | } |
||
3113 | |||
3114 | $parent_new_id = Database::escape_string($parent_new_id); |
||
3115 | $sql = "UPDATE $table_item SET parent_item_id = '$parent_new_id' |
||
3116 | WHERE c_id = ".$this->destination_course_id." AND id = $new_item_id"; |
||
3117 | Database::query($sql); |
||
3118 | } |
||
3119 | |||
3120 | foreach ($previous_item_ids as $new_item_id => $previous_item_old_id) { |
||
3121 | $new_item_id = (int) $new_item_id; |
||
3122 | $previous_new_id = 0; |
||
3123 | if ($previous_item_old_id != 0) { |
||
3124 | $previous_new_id = isset($new_item_ids[$previous_item_old_id]) ? $new_item_ids[$previous_item_old_id] : 0; |
||
3125 | } |
||
3126 | $previous_new_id = Database::escape_string($previous_new_id); |
||
3127 | $sql = "UPDATE $table_item SET previous_item_id = '$previous_new_id' |
||
3128 | WHERE c_id = ".$this->destination_course_id." AND id = '".$new_item_id."'"; |
||
3129 | Database::query($sql); |
||
3130 | } |
||
3131 | |||
3132 | foreach ($next_item_ids as $new_item_id => $next_item_old_id) { |
||
3133 | $new_item_id = (int) $new_item_id; |
||
3134 | $next_new_id = 0; |
||
3135 | if ($next_item_old_id != 0) { |
||
3136 | $next_new_id = isset($new_item_ids[$next_item_old_id]) ? $new_item_ids[$next_item_old_id] : 0; |
||
3137 | } |
||
3138 | $next_new_id = Database::escape_string($next_new_id); |
||
3139 | $sql = "UPDATE $table_item SET next_item_id = '$next_new_id' |
||
3140 | WHERE c_id = ".$this->destination_course_id." AND id = '".$new_item_id."'"; |
||
3141 | Database::query($sql); |
||
3142 | } |
||
3143 | |||
3144 | foreach ($prerequisite_ids as $new_item_id => $prerequisite_old_id) { |
||
3145 | $new_item_id = (int) $new_item_id; |
||
3146 | $prerequisite_new_id = 0; |
||
3147 | if ($prerequisite_old_id != 0) { |
||
3148 | $prerequisite_new_id = $new_item_ids[$prerequisite_old_id]; |
||
3149 | } |
||
3150 | $prerequisite_new_id = Database::escape_string($prerequisite_new_id); |
||
3151 | $sql = "UPDATE $table_item SET prerequisite = '$prerequisite_new_id' |
||
3152 | WHERE c_id = ".$this->destination_course_id." AND id = $new_item_id"; |
||
3153 | Database::query($sql); |
||
3154 | } |
||
3155 | $this->course->resources[RESOURCE_LEARNPATH][$id]->destination_id = $new_lp_id; |
||
3156 | } |
||
3157 | } |
||
3158 | } |
||
3159 | } |
||
3160 | |||
3161 | /** |
||
3162 | * Copy all directory and sub directory. |
||
3163 | * |
||
3164 | * @param string $source The path origin |
||
3165 | * @param string $dest The path destination |
||
3166 | * @param bool Option Overwrite |
||
3167 | * |
||
3168 | * @deprecated |
||
3169 | */ |
||
3170 | public function allow_create_all_directory($source, $dest, $overwrite = false) |
||
3171 | { |
||
3172 | if (!is_dir($dest)) { |
||
3173 | mkdir($dest, api_get_permissions_for_new_directories()); |
||
3174 | } |
||
3175 | if ($handle = opendir($source)) { |
||
3176 | // if the folder exploration is sucsessful, continue |
||
3177 | while (false !== ($file = readdir($handle))) { |
||
3178 | // as long as storing the next file to $file is successful, continue |
||
3179 | if ($file != '.' && $file != '..') { |
||
3180 | $path = $source.'/'.$file; |
||
3181 | if (is_file($path)) { |
||
3182 | /* if (!is_file($dest . '/' . $file) || $overwrite) |
||
3183 | if (!@copy($path, $dest . '/' . $file)) { |
||
3184 | echo '<font color="red">File ('.$path.') '.get_lang('NotHavePermission').'</font>'; |
||
3185 | }*/ |
||
3186 | } elseif (is_dir($path)) { |
||
3187 | if (!is_dir($dest.'/'.$file)) { |
||
3188 | mkdir($dest.'/'.$file); |
||
3189 | } |
||
3190 | self:: allow_create_all_directory($path, $dest.'/'.$file, $overwrite); |
||
3191 | } |
||
3192 | } |
||
3193 | } |
||
3194 | closedir($handle); |
||
3195 | } |
||
3196 | } |
||
3197 | |||
3198 | /** |
||
3199 | * Gets the new ID of one specific tool item from the tool name and the old ID. |
||
3200 | * |
||
3201 | * @param string Tool name |
||
3202 | * @param int Old ID |
||
3203 | * |
||
3204 | * @return int New ID |
||
3205 | */ |
||
3206 | public function get_new_id($tool, $ref) |
||
3207 | { |
||
3208 | // Check if the value exist in the current array. |
||
3209 | if ($tool === 'hotpotatoes') { |
||
3210 | $tool = 'document'; |
||
3211 | } |
||
3212 | |||
3213 | if ($tool === 'student_publication') { |
||
3214 | $tool = RESOURCE_WORK; |
||
3215 | } |
||
3216 | |||
3217 | if ('xapi' === $tool && $this->isXapiEnabled) { |
||
3218 | $tool = RESOURCE_XAPI_TOOL; |
||
3219 | } |
||
3220 | |||
3221 | if (isset($this->course->resources[$tool][$ref]) && |
||
3222 | isset($this->course->resources[$tool][$ref]->destination_id) && |
||
3223 | !empty($this->course->resources[$tool][$ref]->destination_id) |
||
3224 | ) { |
||
3225 | return $this->course->resources[$tool][$ref]->destination_id; |
||
3226 | } |
||
3227 | |||
3228 | // Check if the course is the same (last hope). |
||
3229 | if ($this->course_origin_id == $this->destination_course_id) { |
||
3230 | return $ref; |
||
3231 | } |
||
3232 | |||
3233 | return ''; |
||
3234 | } |
||
3235 | |||
3236 | /** |
||
3237 | * Restore glossary. |
||
3238 | */ |
||
3239 | public function restore_glossary($sessionId = 0) |
||
3240 | { |
||
3241 | $sessionId = (int) $sessionId; |
||
3242 | if ($this->course->has_resources(RESOURCE_GLOSSARY)) { |
||
3243 | $table_glossary = Database::get_course_table(TABLE_GLOSSARY); |
||
3244 | $resources = $this->course->resources; |
||
3245 | foreach ($resources[RESOURCE_GLOSSARY] as $id => $glossary) { |
||
3246 | $params = []; |
||
3247 | if (!empty($sessionId)) { |
||
3248 | $params['session_id'] = $sessionId; |
||
3249 | } |
||
3250 | |||
3251 | // check resources inside html from ckeditor tool and copy correct urls into recipient course |
||
3252 | $glossary->description = DocumentManager::replaceUrlWithNewCourseCode( |
||
3253 | $glossary->description, |
||
3254 | $this->course->code, |
||
3255 | $this->course->destination_path, |
||
3256 | $this->course->backup_path, |
||
3257 | $this->course->info['path'] |
||
3258 | ); |
||
3259 | |||
3260 | $params['c_id'] = $this->destination_course_id; |
||
3261 | $params['description'] = ($glossary->description === false ? '' : self::DBUTF8($glossary->description)); |
||
3262 | $params['display_order'] = $glossary->display_order; |
||
3263 | $params['name'] = self::DBUTF8($glossary->name); |
||
3264 | $params['glossary_id'] = 0; |
||
3265 | $my_id = Database::insert($table_glossary, $params); |
||
3266 | if ($my_id) { |
||
3267 | $sql = "UPDATE $table_glossary SET glossary_id = iid WHERE iid = $my_id"; |
||
3268 | Database::query($sql); |
||
3269 | |||
3270 | api_item_property_update( |
||
3271 | $this->destination_course_info, |
||
3272 | TOOL_GLOSSARY, |
||
3273 | $my_id, |
||
3274 | 'GlossaryAdded', |
||
3275 | api_get_user_id(), |
||
3276 | null, |
||
3277 | null, |
||
3278 | null, |
||
3279 | null, |
||
3280 | $sessionId |
||
3281 | ); |
||
3282 | |||
3283 | if (!isset($this->course->resources[RESOURCE_GLOSSARY][$id])) { |
||
3284 | $this->course->resources[RESOURCE_GLOSSARY][$id] = new stdClass(); |
||
3285 | } |
||
3286 | |||
3287 | $this->course->resources[RESOURCE_GLOSSARY][$id]->destination_id = $my_id; |
||
3288 | } |
||
3289 | } |
||
3290 | } |
||
3291 | } |
||
3292 | |||
3293 | /** |
||
3294 | * @param int $sessionId |
||
3295 | */ |
||
3296 | public function restore_wiki($sessionId = 0) |
||
3297 | { |
||
3298 | if ($this->course->has_resources(RESOURCE_WIKI)) { |
||
3299 | // wiki table of the target course |
||
3300 | $table_wiki = Database::get_course_table(TABLE_WIKI); |
||
3301 | $table_wiki_conf = Database::get_course_table(TABLE_WIKI_CONF); |
||
3302 | |||
3303 | // storing all the resources that have to be copied in an array |
||
3304 | $resources = $this->course->resources; |
||
3305 | |||
3306 | foreach ($resources[RESOURCE_WIKI] as $id => $wiki) { |
||
3307 | // the sql statement to insert the groups from the old course to the new course |
||
3308 | // check resources inside html from ckeditor tool and copy correct urls into recipient course |
||
3309 | $wiki->content = DocumentManager::replaceUrlWithNewCourseCode( |
||
3310 | $wiki->content, |
||
3311 | $this->course->code, |
||
3312 | $this->course->destination_path, |
||
3313 | $this->course->backup_path, |
||
3314 | $this->course->info['path'] |
||
3315 | ); |
||
3316 | |||
3317 | $params = [ |
||
3318 | 'c_id' => $this->destination_course_id, |
||
3319 | 'page_id' => self::DBUTF8($wiki->page_id), |
||
3320 | 'reflink' => self::DBUTF8($wiki->reflink), |
||
3321 | 'title' => self::DBUTF8($wiki->title), |
||
3322 | 'content' => ($wiki->content === false ? '' : self::DBUTF8($wiki->content)), |
||
3323 | 'user_id' => intval($wiki->user_id), |
||
3324 | 'group_id' => intval($wiki->group_id), |
||
3325 | 'dtime' => self::DBUTF8($wiki->dtime), |
||
3326 | 'progress' => self::DBUTF8($wiki->progress), |
||
3327 | 'version' => intval($wiki->version), |
||
3328 | 'session_id' => !empty($sessionId) ? intval($sessionId) : 0, |
||
3329 | 'addlock' => 0, |
||
3330 | 'editlock' => 0, |
||
3331 | 'visibility' => 0, |
||
3332 | 'addlock_disc' => 0, |
||
3333 | 'visibility_disc' => 0, |
||
3334 | 'ratinglock_disc' => 0, |
||
3335 | 'assignment' => 0, |
||
3336 | 'comment' => '', |
||
3337 | 'is_editing' => 0, |
||
3338 | 'linksto' => 0, |
||
3339 | 'tag' => '', |
||
3340 | 'user_ip' => '', |
||
3341 | ]; |
||
3342 | |||
3343 | $new_id = Database::insert($table_wiki, $params); |
||
3344 | |||
3345 | if ($new_id) { |
||
3346 | $sql = "UPDATE $table_wiki SET page_id = '$new_id', id = iid |
||
3347 | WHERE c_id = ".$this->destination_course_id." AND iid = '$new_id'"; |
||
3348 | Database::query($sql); |
||
3349 | |||
3350 | $this->course->resources[RESOURCE_WIKI][$id]->destination_id = $new_id; |
||
3351 | |||
3352 | // we also add an entry in wiki_conf |
||
3353 | $params = [ |
||
3354 | 'c_id' => $this->destination_course_id, |
||
3355 | 'page_id' => $new_id, |
||
3356 | 'task' => '', |
||
3357 | 'feedback1' => '', |
||
3358 | 'feedback2' => '', |
||
3359 | 'feedback3' => '', |
||
3360 | 'fprogress1' => '', |
||
3361 | 'fprogress2' => '', |
||
3362 | 'fprogress3' => '', |
||
3363 | 'max_size' => 0, |
||
3364 | 'max_text' => 0, |
||
3365 | 'max_version' => 0, |
||
3366 | 'startdate_assig' => null, |
||
3367 | 'enddate_assig' => null, |
||
3368 | 'delayedsubmit' => 0, |
||
3369 | ]; |
||
3370 | |||
3371 | Database::insert($table_wiki_conf, $params); |
||
3372 | } |
||
3373 | } |
||
3374 | } |
||
3375 | } |
||
3376 | |||
3377 | /** |
||
3378 | * Restore xapi tool |
||
3379 | * |
||
3380 | * @param int $sessionId |
||
3381 | */ |
||
3382 | |||
3383 | public function restore_xapi_tool() |
||
3384 | { |
||
3385 | if ($this->course->has_resources(RESOURCE_XAPI_TOOL) && $this->isXapiEnabled) { |
||
3386 | $resources = $this->course->resources; |
||
3387 | foreach ($resources[RESOURCE_XAPI_TOOL] as $id => $xapiTool) { |
||
3388 | |||
3389 | $launchPath = str_replace( |
||
3390 | api_get_path(WEB_COURSE_PATH).$this->course->info['path'].'/', |
||
3391 | '', |
||
3392 | dirname($xapiTool->params['launch_url']) |
||
3393 | ); |
||
3394 | |||
3395 | $originPath = $this->course->backup_path.'/'.$launchPath; |
||
3396 | $destinationPath = api_get_path(SYS_COURSE_PATH).$this->course->destination_path.'/'.$launchPath; |
||
3397 | $xapiDir = dirname($destinationPath); |
||
3398 | @mkdir($xapiDir, api_get_permissions_for_new_directories(), true); |
||
3399 | if (copyDirTo($originPath, $destinationPath, false)) { |
||
3400 | $xapiTool->params['launch_url'] = str_replace( |
||
3401 | '/'.$this->course->info['path'].'/', |
||
3402 | '/'.$this->course->destination_path.'/', |
||
3403 | $xapiTool->params['launch_url'] |
||
3404 | ); |
||
3405 | $ref = $xapiTool->params['id']; |
||
3406 | $xapiTool->params['c_id'] = $this->destination_course_id; |
||
3407 | unset($xapiTool->params['id']); |
||
3408 | |||
3409 | $lastId = Database::insert('xapi_tool_launch', $xapiTool->params, false); |
||
3410 | $this->course->resources[RESOURCE_XAPI_TOOL][$ref]->destination_id = $lastId; |
||
3411 | } |
||
3412 | } |
||
3413 | } |
||
3414 | } |
||
3415 | |||
3416 | /** |
||
3417 | * Restore Thematics. |
||
3418 | * |
||
3419 | * @param int $sessionId |
||
3420 | */ |
||
3421 | public function restore_thematic($sessionId = 0) |
||
3422 | { |
||
3423 | if ($this->course->has_resources(RESOURCE_THEMATIC)) { |
||
3424 | $table_thematic = Database::get_course_table(TABLE_THEMATIC); |
||
3425 | $table_thematic_advance = Database::get_course_table(TABLE_THEMATIC_ADVANCE); |
||
3426 | $table_thematic_plan = Database::get_course_table(TABLE_THEMATIC_PLAN); |
||
3427 | |||
3428 | $resources = $this->course->resources; |
||
3429 | foreach ($resources[RESOURCE_THEMATIC] as $id => $thematic) { |
||
3430 | // check resources inside html from ckeditor tool and copy correct urls into recipient course |
||
3431 | $thematic->params['content'] = DocumentManager::replaceUrlWithNewCourseCode( |
||
3432 | $thematic->params['content'], |
||
3433 | $this->course->code, |
||
3434 | $this->course->destination_path, |
||
3435 | $this->course->backup_path, |
||
3436 | $this->course->info['path'] |
||
3437 | ); |
||
3438 | $thematic->params['c_id'] = $this->destination_course_id; |
||
3439 | unset($thematic->params['id']); |
||
3440 | unset($thematic->params['iid']); |
||
3441 | |||
3442 | $last_id = Database::insert($table_thematic, $thematic->params, false); |
||
3443 | |||
3444 | if ($last_id) { |
||
3445 | $sql = "UPDATE $table_thematic SET id = iid WHERE iid = $last_id"; |
||
3446 | Database::query($sql); |
||
3447 | |||
3448 | api_item_property_update( |
||
3449 | $this->destination_course_info, |
||
3450 | 'thematic', |
||
3451 | $last_id, |
||
3452 | 'ThematicAdded', |
||
3453 | api_get_user_id(), |
||
3454 | null, |
||
3455 | null, |
||
3456 | null, |
||
3457 | null, |
||
3458 | $sessionId |
||
3459 | ); |
||
3460 | |||
3461 | foreach ($thematic->thematic_advance_list as $thematic_advance) { |
||
3462 | unset($thematic_advance['id']); |
||
3463 | unset($thematic_advance['iid']); |
||
3464 | $thematic_advance['attendance_id'] = 0; |
||
3465 | $thematic_advance['thematic_id'] = $last_id; |
||
3466 | $thematic_advance['c_id'] = $this->destination_course_id; |
||
3467 | |||
3468 | $my_id = Database::insert( |
||
3469 | $table_thematic_advance, |
||
3470 | $thematic_advance, |
||
3471 | false |
||
3472 | ); |
||
3473 | |||
3474 | if ($my_id) { |
||
3475 | $sql = "UPDATE $table_thematic_advance SET id = iid WHERE iid = $my_id"; |
||
3476 | Database::query($sql); |
||
3477 | |||
3478 | api_item_property_update( |
||
3479 | $this->destination_course_info, |
||
3480 | 'thematic_advance', |
||
3481 | $my_id, |
||
3482 | 'ThematicAdvanceAdded', |
||
3483 | api_get_user_id(), |
||
3484 | null, |
||
3485 | null, |
||
3486 | null, |
||
3487 | null, |
||
3488 | $sessionId |
||
3489 | ); |
||
3490 | } |
||
3491 | } |
||
3492 | |||
3493 | foreach ($thematic->thematic_plan_list as $thematic_plan) { |
||
3494 | unset($thematic_plan['id']); |
||
3495 | unset($thematic_plan['iid']); |
||
3496 | $thematic_plan['thematic_id'] = $last_id; |
||
3497 | $thematic_plan['c_id'] = $this->destination_course_id; |
||
3498 | $my_id = Database::insert($table_thematic_plan, $thematic_plan, false); |
||
3499 | |||
3500 | if ($my_id) { |
||
3501 | $sql = "UPDATE $table_thematic_plan SET id = iid WHERE iid = $my_id"; |
||
3502 | Database::query($sql); |
||
3503 | |||
3504 | api_item_property_update( |
||
3505 | $this->destination_course_info, |
||
3506 | 'thematic_plan', |
||
3507 | $my_id, |
||
3508 | 'ThematicPlanAdded', |
||
3509 | api_get_user_id(), |
||
3510 | null, |
||
3511 | null, |
||
3512 | null, |
||
3513 | null, |
||
3514 | $sessionId |
||
3515 | ); |
||
3516 | } |
||
3517 | } |
||
3518 | } |
||
3519 | } |
||
3520 | } |
||
3521 | } |
||
3522 | |||
3523 | /** |
||
3524 | * Restore Attendance. |
||
3525 | * |
||
3526 | * @param int $sessionId |
||
3527 | */ |
||
3528 | public function restore_attendance($sessionId = 0) |
||
3529 | { |
||
3530 | if ($this->course->has_resources(RESOURCE_ATTENDANCE)) { |
||
3531 | $table_attendance = Database::get_course_table(TABLE_ATTENDANCE); |
||
3532 | $table_attendance_calendar = Database::get_course_table(TABLE_ATTENDANCE_CALENDAR); |
||
3533 | |||
3534 | $resources = $this->course->resources; |
||
3535 | foreach ($resources[RESOURCE_ATTENDANCE] as $id => $obj) { |
||
3536 | // check resources inside html from ckeditor tool and copy correct urls into recipient course |
||
3537 | $obj->params['description'] = DocumentManager::replaceUrlWithNewCourseCode( |
||
3538 | $obj->params['description'], |
||
3539 | $this->course->code, |
||
3540 | $this->course->destination_path, |
||
3541 | $this->course->backup_path, |
||
3542 | $this->course->info['path'] |
||
3543 | ); |
||
3544 | |||
3545 | unset($obj->params['id']); |
||
3546 | unset($obj->params['iid']); |
||
3547 | $obj->params['c_id'] = $this->destination_course_id; |
||
3548 | $last_id = Database::insert($table_attendance, $obj->params); |
||
3549 | |||
3550 | if (is_numeric($last_id)) { |
||
3551 | $sql = "UPDATE $table_attendance SET id = iid WHERE iid = $last_id"; |
||
3552 | Database::query($sql); |
||
3553 | |||
3554 | $this->course->resources[RESOURCE_ATTENDANCE][$id]->destination_id = $last_id; |
||
3555 | |||
3556 | api_item_property_update( |
||
3557 | $this->destination_course_info, |
||
3558 | TOOL_ATTENDANCE, |
||
3559 | $last_id, |
||
3560 | 'AttendanceAdded', |
||
3561 | api_get_user_id(), |
||
3562 | null, |
||
3563 | null, |
||
3564 | null, |
||
3565 | null, |
||
3566 | $sessionId |
||
3567 | ); |
||
3568 | |||
3569 | foreach ($obj->attendance_calendar as $attendance_calendar) { |
||
3570 | unset($attendance_calendar['id']); |
||
3571 | unset($attendance_calendar['iid']); |
||
3572 | |||
3573 | $attendance_calendar['attendance_id'] = $last_id; |
||
3574 | $attendance_calendar['c_id'] = $this->destination_course_id; |
||
3575 | $attendanceCalendarId = Database::insert( |
||
3576 | $table_attendance_calendar, |
||
3577 | $attendance_calendar |
||
3578 | ); |
||
3579 | |||
3580 | $sql = "UPDATE $table_attendance_calendar SET id = iid WHERE iid = $attendanceCalendarId"; |
||
3581 | Database::query($sql); |
||
3582 | } |
||
3583 | } |
||
3584 | } |
||
3585 | } |
||
3586 | } |
||
3587 | |||
3588 | /** |
||
3589 | * Restore Works. |
||
3590 | * |
||
3591 | * @param int $sessionId |
||
3592 | */ |
||
3593 | public function restore_works($sessionId = 0) |
||
3594 | { |
||
3595 | require_once api_get_path(SYS_CODE_PATH).'work/work.lib.php'; |
||
3596 | if ($this->course->has_resources(RESOURCE_WORK)) { |
||
3597 | $table = Database::get_course_table(TABLE_STUDENT_PUBLICATION_ASSIGNMENT); |
||
3598 | |||
3599 | $resources = $this->course->resources; |
||
3600 | foreach ($resources[RESOURCE_WORK] as $obj) { |
||
3601 | // check resources inside html from ckeditor tool and copy correct urls into recipient course |
||
3602 | $obj->params['description'] = DocumentManager::replaceUrlWithNewCourseCode( |
||
3603 | $obj->params['description'], |
||
3604 | $this->course->code, |
||
3605 | $this->course->destination_path, |
||
3606 | $this->course->backup_path, |
||
3607 | $this->course->info['path'] |
||
3608 | ); |
||
3609 | |||
3610 | $id_work = $obj->params['id']; |
||
3611 | $obj->params['id'] = null; |
||
3612 | $obj->params['c_id'] = $this->destination_course_info['real_id']; |
||
3613 | |||
3614 | // re-create dir |
||
3615 | // @todo check security against injection of dir in crafted course backup here! |
||
3616 | $path = $obj->params['url']; |
||
3617 | $path = '/'.str_replace('/', '', substr($path, 1)); |
||
3618 | |||
3619 | $workData = []; |
||
3620 | |||
3621 | switch ($this->file_option) { |
||
3622 | case FILE_SKIP: |
||
3623 | $workData = get_work_data_by_path( |
||
3624 | $path, |
||
3625 | $this->destination_course_info['real_id'] |
||
3626 | ); |
||
3627 | if (!empty($workData)) { |
||
3628 | break; |
||
3629 | } |
||
3630 | break; |
||
3631 | case FILE_OVERWRITE: |
||
3632 | if (!empty($this->course_origin_id)) { |
||
3633 | $sql = 'SELECT * FROM '.$table.' |
||
3634 | WHERE |
||
3635 | c_id = '.$this->course_origin_id.' AND |
||
3636 | publication_id = '.$id_work; |
||
3637 | $result = Database::query($sql); |
||
3638 | $cant = Database::num_rows($result); |
||
3639 | if ($cant > 0) { |
||
3640 | $row = Database::fetch_assoc($result); |
||
3641 | } |
||
3642 | |||
3643 | $obj->params['enableExpiryDate'] = empty($row['expires_on']) ? false : true; |
||
3644 | $obj->params['enableEndDate'] = empty($row['ends_on']) ? false : true; |
||
3645 | $obj->params['expires_on'] = $row['expires_on']; |
||
3646 | $obj->params['ends_on'] = $row['ends_on']; |
||
3647 | $obj->params['enable_qualification'] = $row['enable_qualification']; |
||
3648 | $obj->params['add_to_calendar'] = !empty($row['add_to_calendar']) ? 1 : 0; |
||
3649 | } |
||
3650 | //no break |
||
3651 | case FILE_RENAME: |
||
3652 | $workData = get_work_data_by_path( |
||
3653 | $path, |
||
3654 | $this->destination_course_info['real_id'] |
||
3655 | ); |
||
3656 | break; |
||
3657 | } |
||
3658 | |||
3659 | $obj->params['work_title'] = $obj->params['title']; |
||
3660 | $obj->params['new_dir'] = $obj->params['title']; |
||
3661 | |||
3662 | if (empty($workData)) { |
||
3663 | $workId = addDir( |
||
3664 | $obj->params, |
||
3665 | api_get_user_id(), |
||
3666 | $this->destination_course_info, |
||
3667 | 0, |
||
3668 | $sessionId |
||
3669 | ); |
||
3670 | $this->course->resources[RESOURCE_WORK][$id_work]->destination_id = $workId; |
||
3671 | } else { |
||
3672 | $workId = $workData['iid']; |
||
3673 | updateWork( |
||
3674 | $workId, |
||
3675 | $obj->params, |
||
3676 | $this->destination_course_info, |
||
3677 | $sessionId |
||
3678 | ); |
||
3679 | updatePublicationAssignment( |
||
3680 | $workId, |
||
3681 | $obj->params, |
||
3682 | $this->destination_course_info, |
||
3683 | 0 |
||
3684 | ); |
||
3685 | $this->course->resources[RESOURCE_WORK][$id_work]->destination_id = $workId; |
||
3686 | } |
||
3687 | } |
||
3688 | } |
||
3689 | } |
||
3690 | |||
3691 | /** |
||
3692 | * Restore gradebook. |
||
3693 | * |
||
3694 | * @param int $sessionId |
||
3695 | * |
||
3696 | * @return bool |
||
3697 | */ |
||
3698 | public function restore_gradebook($sessionId = 0) |
||
3699 | { |
||
3700 | if (in_array($this->file_option, [FILE_SKIP, FILE_RENAME])) { |
||
3701 | return false; |
||
3702 | } |
||
3703 | // if overwrite |
||
3704 | if ($this->course->has_resources(RESOURCE_GRADEBOOK)) { |
||
3705 | $resources = $this->course->resources; |
||
3706 | $destinationCourseCode = $this->destination_course_info['code']; |
||
3707 | // Delete destination gradebook |
||
3708 | $cats = \Category:: load( |
||
3709 | null, |
||
3710 | null, |
||
3711 | $destinationCourseCode, |
||
3712 | null, |
||
3713 | null, |
||
3714 | $sessionId |
||
3715 | ); |
||
3716 | |||
3717 | if (!empty($cats)) { |
||
3718 | /** @var \Category $cat */ |
||
3719 | foreach ($cats as $cat) { |
||
3720 | $cat->delete_all(); |
||
3721 | } |
||
3722 | } |
||
3723 | |||
3724 | /** @var GradeBookBackup $obj */ |
||
3725 | foreach ($resources[RESOURCE_GRADEBOOK] as $id => $obj) { |
||
3726 | if (!empty($obj->categories)) { |
||
3727 | $categoryIdList = []; |
||
3728 | /** @var \Category $cat */ |
||
3729 | foreach ($obj->categories as $cat) { |
||
3730 | $cat->set_course_code($destinationCourseCode); |
||
3731 | $cat->set_session_id($sessionId); |
||
3732 | |||
3733 | $parentId = $cat->get_parent_id(); |
||
3734 | if (!empty($parentId)) { |
||
3735 | if (isset($categoryIdList[$parentId])) { |
||
3736 | $cat->set_parent_id($categoryIdList[$parentId]); |
||
3737 | } |
||
3738 | } |
||
3739 | $oldId = $cat->get_id(); |
||
3740 | $categoryId = $cat->add(); |
||
3741 | $categoryIdList[$oldId] = $categoryId; |
||
3742 | if (!empty($cat->evaluations)) { |
||
3743 | /** @var \Evaluation $evaluation */ |
||
3744 | foreach ($cat->evaluations as $evaluation) { |
||
3745 | $evaluation->set_category_id($categoryId); |
||
3746 | $evaluation->set_course_code($destinationCourseCode); |
||
3747 | $evaluation->setSessionId($sessionId); |
||
3748 | $evaluation->add(); |
||
3749 | } |
||
3750 | } |
||
3751 | |||
3752 | if (!empty($cat->links)) { |
||
3753 | /** @var \AbstractLink $link */ |
||
3754 | foreach ($cat->links as $link) { |
||
3755 | $link->set_category_id($categoryId); |
||
3756 | $link->set_course_code($destinationCourseCode); |
||
3757 | $link->set_session_id($sessionId); |
||
3758 | $import = false; |
||
3759 | $itemId = $link->get_ref_id(); |
||
3760 | switch ($link->get_type()) { |
||
3761 | case LINK_EXERCISE: |
||
3762 | $type = RESOURCE_QUIZ; |
||
3763 | break; |
||
3764 | /*case LINK_DROPBOX: |
||
3765 | break;*/ |
||
3766 | case LINK_STUDENTPUBLICATION: |
||
3767 | $type = RESOURCE_WORK; |
||
3768 | break; |
||
3769 | case LINK_LEARNPATH: |
||
3770 | $type = RESOURCE_LEARNPATH; |
||
3771 | break; |
||
3772 | case LINK_FORUM_THREAD: |
||
3773 | $type = RESOURCE_FORUMTOPIC; |
||
3774 | break; |
||
3775 | case LINK_ATTENDANCE: |
||
3776 | $type = RESOURCE_ATTENDANCE; |
||
3777 | break; |
||
3778 | case LINK_SURVEY: |
||
3779 | $type = RESOURCE_ATTENDANCE; |
||
3780 | break; |
||
3781 | case LINK_HOTPOTATOES: |
||
3782 | $type = RESOURCE_QUIZ; |
||
3783 | break; |
||
3784 | } |
||
3785 | |||
3786 | if ($this->course->has_resources($type) && |
||
3787 | isset($this->course->resources[$type][$itemId]) |
||
3788 | ) { |
||
3789 | $item = $this->course->resources[$type][$itemId]; |
||
3790 | if ($item && $item->is_restored()) { |
||
3791 | $link->set_ref_id($item->destination_id); |
||
3792 | $import = true; |
||
3793 | } |
||
3794 | } |
||
3795 | |||
3796 | if ($import) { |
||
3797 | $link->add(); |
||
3798 | } |
||
3799 | } |
||
3800 | } |
||
3801 | } |
||
3802 | } |
||
3803 | } |
||
3804 | } |
||
3805 | } |
||
3806 | |||
3807 | /** |
||
3808 | * Restore course assets (not included in documents). |
||
3809 | */ |
||
3810 | public function restore_assets() |
||
3811 | { |
||
3812 | if ($this->course->has_resources(RESOURCE_ASSET)) { |
||
3813 | $resources = $this->course->resources; |
||
3814 | $path = api_get_path(SYS_COURSE_PATH).$this->course->destination_path.'/'; |
||
3815 | |||
3816 | foreach ($resources[RESOURCE_ASSET] as $asset) { |
||
3817 | if (is_file($this->course->backup_path.'/'.$asset->path) && |
||
3818 | is_readable($this->course->backup_path.'/'.$asset->path) && |
||
3819 | is_dir(dirname($path.$asset->path)) && |
||
3820 | is_writeable(dirname($path.$asset->path)) |
||
3821 | ) { |
||
3822 | switch ($this->file_option) { |
||
3823 | case FILE_SKIP: |
||
3824 | break; |
||
3825 | case FILE_OVERWRITE: |
||
3826 | copy( |
||
3827 | $this->course->backup_path.'/'.$asset->path, |
||
3828 | $path.$asset->path |
||
3829 | ); |
||
3830 | break; |
||
3831 | } |
||
3832 | } |
||
3833 | } |
||
3834 | } |
||
3835 | } |
||
3836 | |||
3837 | /** |
||
3838 | * @param string $str |
||
3839 | * |
||
3840 | * @return string |
||
3841 | */ |
||
3842 | public function DBUTF8($str) |
||
3843 | { |
||
3844 | if (UTF8_CONVERT) { |
||
3845 | $str = utf8_encode($str); |
||
3846 | } |
||
3847 | |||
3848 | return $str; |
||
3849 | } |
||
3850 | |||
3851 | /** |
||
3852 | * @param string $str |
||
3853 | * |
||
3854 | * @return string |
||
3855 | */ |
||
3856 | public function DBUTF8escapestring($str) |
||
3857 | { |
||
3858 | if (UTF8_CONVERT) { |
||
3859 | $str = utf8_encode($str); |
||
3860 | } |
||
3861 | |||
3862 | return Database::escape_string($str); |
||
3863 | } |
||
3864 | |||
3865 | /** |
||
3866 | * @param array $array |
||
3867 | * |
||
3868 | * @return mixed |
||
3869 | */ |
||
3870 | public function DBUTF8_array($array) |
||
3871 | { |
||
3872 | if (UTF8_CONVERT) { |
||
3873 | foreach ($array as &$item) { |
||
3874 | $item = utf8_encode($item); |
||
3875 | } |
||
3876 | |||
3877 | return $array; |
||
3878 | } else { |
||
3879 | return $array; |
||
3880 | } |
||
3881 | } |
||
3882 | |||
3883 | /** |
||
3884 | * @param int $groupId |
||
3885 | * |
||
3886 | * @return array |
||
3887 | */ |
||
3888 | public function checkGroupId($groupId) |
||
3891 | } |
||
3892 | |||
3893 | /** |
||
3894 | * @param string $documentPath |
||
3895 | * @param string $webEditorCss |
||
3896 | */ |
||
3897 | public function fixEditorHtmlContent($documentPath, $webEditorCss = '') |
||
3898 | { |
||
3899 | $extension = pathinfo(basename($documentPath), PATHINFO_EXTENSION); |
||
3900 | |||
3901 | switch ($extension) { |
||
3902 | case 'html': |
||
3903 | case 'htm': |
||
3904 | $contents = file_get_contents($documentPath); |
||
3905 | $contents = str_replace( |
||
3906 | '{{css_editor}}', |
||
3907 | $webEditorCss, |
||
3908 | $contents |
||
3909 | ); |
||
3910 | file_put_contents($documentPath, $contents); |
||
3911 | break; |
||
3912 | } |
||
3913 | } |
||
3914 | |||
3915 | /** |
||
3916 | * Check if user exist otherwise use current user. |
||
3917 | * |
||
3918 | * @param int $userId |
||
3919 | * @param bool $returnNull |
||
3920 | * |
||
3921 | * @return int |
||
3922 | */ |
||
3923 | private function checkUserId($userId, $returnNull = false) |
||
3941 | } |
||
3942 | } |
||
3943 |