Passed
Pull Request — 1.11.x (#5783)
by Yannick
08:32
created

CourseExport   A

Complexity

Total Complexity 28

Size/Duplication

Total Lines 310
Duplicated Lines 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
wmc 28
eloc 191
c 1
b 0
f 0
dl 0
loc 310
rs 10

12 Methods

Rating   Name   Duplication   Size   Complexity  
A createFiltersXml() 0 16 2
A exportCourse() 0 17 2
A __construct() 0 8 2
B createInforefXml() 0 39 7
A createCalendarXml() 0 18 2
B createCourseXml() 0 66 1
A createCommentsXml() 0 16 2
A createEnrolmentsXml() 0 17 2
A createCompetenciesXml() 0 13 2
A createCompletionDefaultsXml() 0 13 2
A createRolesXml() 0 13 2
A createContentBankXml() 0 12 2
1
<?php
2
3
/* For licensing terms, see /license.txt */
4
5
namespace moodleexport;
6
7
use Exception;
8
9
/**
10
 * Class CourseExport.
11
 *
12
 * @package moodleexport
13
 */
14
class CourseExport
15
{
16
    private $course;
17
    private $courseInfo;
18
    private $activities;
19
20
    public function __construct($course, $activities)
21
    {
22
        $this->course = $course;
23
        $this->courseInfo = api_get_course_info($course->code);
24
        $this->activities = $activities;
25
26
        if (!$this->courseInfo) {
27
            throw new Exception("Course not found.");
28
        }
29
    }
30
31
    /**
32
     * Export the course-related files to the appropriate directory.
33
     */
34
    public function exportCourse(string $exportDir): void
35
    {
36
        $courseDir = $exportDir . '/course';
37
        if (!is_dir($courseDir)) {
38
            mkdir($courseDir, api_get_permissions_for_new_directories(), true);
39
        }
40
41
        $this->createCourseXml($courseDir);
42
        $this->createEnrolmentsXml($this->courseInfo['enrolments'] ?? [], $courseDir);
43
        $this->createInforefXml($courseDir);
44
        $this->createRolesXml($this->courseInfo['roles'] ?? [], $courseDir);
45
        $this->createCalendarXml($this->courseInfo['calendar'] ?? [], $courseDir);
46
        $this->createCommentsXml($this->courseInfo['comments'] ?? [], $courseDir);
47
        $this->createCompetenciesXml($this->courseInfo['competencies'] ?? [], $courseDir);
48
        $this->createCompletionDefaultsXml($this->courseInfo['completiondefaults'] ?? [], $courseDir);
49
        $this->createContentBankXml($this->courseInfo['contentbank'] ?? [], $courseDir);
50
        $this->createFiltersXml($this->courseInfo['filters'] ?? [], $courseDir);
51
    }
52
53
    /**
54
     * Create course.xml based on the course data from MoodleExport.
55
     */
56
    private function createCourseXml(string $destinationDir): void
57
    {
58
        $courseId = $this->courseInfo['real_id'] ?? 0;
59
        $contextId = $this->courseInfo['real_id'] ?? 1;
60
        $shortname = $this->courseInfo['code'] ?? 'Unknown Course';
61
        $fullname = $this->courseInfo['title'] ?? 'Unknown Fullname';
62
        $showgrades = $this->courseInfo['showgrades'] ?? 0;
63
        $startdate = $this->courseInfo['startdate'] ?? time();
64
        $enddate = $this->courseInfo['enddate'] ?? time() + (60 * 60 * 24 * 365);
65
        $visible = $this->courseInfo['visible'] ?? 1;
66
        $enablecompletion = $this->courseInfo['enablecompletion'] ?? 0;
67
68
        $xmlContent = '<?xml version="1.0" encoding="UTF-8"?>' . PHP_EOL;
69
        $xmlContent .= '<course id="' . $courseId . '" contextid="' . $contextId . '">' . PHP_EOL;
70
        $xmlContent .= '  <shortname>' . htmlspecialchars($shortname) . '</shortname>' . PHP_EOL;
71
        $xmlContent .= '  <fullname>' . htmlspecialchars($fullname) . '</fullname>' . PHP_EOL;
72
        $xmlContent .= '  <idnumber></idnumber>' . PHP_EOL;
73
        $xmlContent .= '  <summary></summary>' . PHP_EOL;
74
        $xmlContent .= '  <summaryformat>1</summaryformat>' . PHP_EOL;
75
        $xmlContent .= '  <format>topics</format>' . PHP_EOL;
76
        $xmlContent .= '  <showgrades>' . $showgrades . '</showgrades>' . PHP_EOL;
77
        $xmlContent .= '  <newsitems>5</newsitems>' . PHP_EOL;
78
        $xmlContent .= '  <startdate>' . $startdate . '</startdate>' . PHP_EOL;
79
        $xmlContent .= '  <enddate>' . $enddate . '</enddate>' . PHP_EOL;
80
        $xmlContent .= '  <marker>0</marker>' . PHP_EOL;
81
        $xmlContent .= '  <maxbytes>0</maxbytes>' . PHP_EOL;
82
        $xmlContent .= '  <legacyfiles>0</legacyfiles>' . PHP_EOL;
83
        $xmlContent .= '  <showreports>0</showreports>' . PHP_EOL;
84
        $xmlContent .= '  <visible>' . $visible . '</visible>' . PHP_EOL;
85
        $xmlContent .= '  <groupmode>0</groupmode>' . PHP_EOL;
86
        $xmlContent .= '  <groupmodeforce>0</groupmodeforce>' . PHP_EOL;
87
        $xmlContent .= '  <defaultgroupingid>0</defaultgroupingid>' . PHP_EOL;
88
        $xmlContent .= '  <lang></lang>' . PHP_EOL;
89
        $xmlContent .= '  <theme></theme>' . PHP_EOL;
90
        $xmlContent .= '  <timecreated>' . time() . '</timecreated>' . PHP_EOL;
91
        $xmlContent .= '  <timemodified>' . time() . '</timemodified>' . PHP_EOL;
92
        $xmlContent .= '  <requested>0</requested>' . PHP_EOL;
93
        $xmlContent .= '  <showactivitydates>1</showactivitydates>' . PHP_EOL;
94
        $xmlContent .= '  <showcompletionconditions>1</showcompletionconditions>' . PHP_EOL;
95
        $xmlContent .= '  <enablecompletion>' . $enablecompletion . '</enablecompletion>' . PHP_EOL;
96
        $xmlContent .= '  <completionnotify>0</completionnotify>' . PHP_EOL;
97
        $xmlContent .= '  <category id="1">' . PHP_EOL;
98
        $xmlContent .= '    <name>Miscellaneous</name>' . PHP_EOL;
99
        $xmlContent .= '    <description>$@NULL@$</description>' . PHP_EOL;
100
        $xmlContent .= '  </category>' . PHP_EOL;
101
        $xmlContent .= '  <tags>' . PHP_EOL;
102
        $xmlContent .= '  </tags>' . PHP_EOL;
103
        $xmlContent .= '  <customfields>' . PHP_EOL;
104
        $xmlContent .= '  </customfields>' . PHP_EOL;
105
        $xmlContent .= '  <courseformatoptions>' . PHP_EOL;
106
        $xmlContent .= '    <courseformatoption>' . PHP_EOL;
107
        $xmlContent .= '      <format>topics</format>' . PHP_EOL;
108
        $xmlContent .= '      <sectionid>0</sectionid>' . PHP_EOL;
109
        $xmlContent .= '      <name>hiddensections</name>' . PHP_EOL;
110
        $xmlContent .= '      <value>0</value>' . PHP_EOL;
111
        $xmlContent .= '    </courseformatoption>' . PHP_EOL;
112
        $xmlContent .= '    <courseformatoption>' . PHP_EOL;
113
        $xmlContent .= '      <format>topics</format>' . PHP_EOL;
114
        $xmlContent .= '      <sectionid>0</sectionid>' . PHP_EOL;
115
        $xmlContent .= '      <name>coursedisplay</name>' . PHP_EOL;
116
        $xmlContent .= '      <value>0</value>' . PHP_EOL;
117
        $xmlContent .= '    </courseformatoption>' . PHP_EOL;
118
        $xmlContent .= '  </courseformatoptions>' . PHP_EOL;
119
        $xmlContent .= '</course>';
120
121
        file_put_contents($destinationDir . '/course.xml', $xmlContent);
122
    }
123
124
    /**
125
     * Create enrolments.xml based on the course data from MoodleExport.
126
     */
127
    private function createEnrolmentsXml(array $enrolmentsData, string $destinationDir): void
128
    {
129
        $xmlContent = '<?xml version="1.0" encoding="UTF-8"?>' . PHP_EOL;
130
        $xmlContent .= '<enrolments>' . PHP_EOL;
131
        foreach ($enrolmentsData as $enrol) {
132
            $id = $enrol['id'] ?? 0;
133
            $type = $enrol['type'] ?? 'manual';
134
            $status = $enrol['status'] ?? 1;
135
136
            $xmlContent .= '  <enrol id="' . $id . '">' . PHP_EOL;
137
            $xmlContent .= '    <enrol>' . htmlspecialchars($type) . '</enrol>' . PHP_EOL;
138
            $xmlContent .= '    <status>' . $status . '</status>' . PHP_EOL;
139
            $xmlContent .= '  </enrol>' . PHP_EOL;
140
        }
141
        $xmlContent .= '</enrolments>';
142
143
        file_put_contents($destinationDir . '/enrolments.xml', $xmlContent);
144
    }
145
146
    /**
147
     * Creates the inforef.xml file with file references, question categories, and role references.
148
     */
149
    private function createInforefXml(string $destinationDir): void
150
    {
151
        $xmlContent = '<?xml version="1.0" encoding="UTF-8"?>' . PHP_EOL;
152
        $xmlContent .= '<inforef>' . PHP_EOL;
153
154
        $questionCategories = [];
155
        foreach ($this->activities as $activity) {
156
            if ($activity['modulename'] === 'quiz') {
157
                $quizExport = new QuizExport($this->course);
158
                $quizData = $quizExport->getData($activity['id'], $activity['sectionid']);
159
                foreach ($quizData['questions'] as $question) {
160
                    $categoryId = $question['questioncategoryid'];
161
                    if (!in_array($categoryId, $questionCategories, true)) {
162
                        $questionCategories[] = $categoryId;
163
                    }
164
                }
165
            }
166
        }
167
168
        if (!empty($questionCategories)) {
169
            $xmlContent .= '  <question_categoryref>' . PHP_EOL;
170
            foreach ($questionCategories as $categoryId) {
171
                $xmlContent .= '    <question_category>' . PHP_EOL;
172
                $xmlContent .= '      <id>' . $categoryId . '</id>' . PHP_EOL;
173
                $xmlContent .= '    </question_category>' . PHP_EOL;
174
            }
175
            $xmlContent .= '  </question_categoryref>' . PHP_EOL;
176
        }
177
178
        // Add role references
179
        $xmlContent .= '  <roleref>' . PHP_EOL;
180
        $xmlContent .= '    <role>' . PHP_EOL;
181
        $xmlContent .= '      <id>5</id>' . PHP_EOL;
182
        $xmlContent .= '    </role>' . PHP_EOL;
183
        $xmlContent .= '  </roleref>' . PHP_EOL;
184
185
        $xmlContent .= '</inforef>' . PHP_EOL;
186
187
        file_put_contents($destinationDir . '/inforef.xml', $xmlContent);
188
    }
189
190
    /**
191
     * Creates the roles.xml file.
192
     */
193
    private function createRolesXml(array $rolesData, string $destinationDir): void
194
    {
195
        $xmlContent = '<?xml version="1.0" encoding="UTF-8"?>' . PHP_EOL;
196
        $xmlContent .= '<roles>' . PHP_EOL;
197
        foreach ($rolesData as $role) {
198
            $roleName = $role['name'] ?? 'Student';
199
            $xmlContent .= '  <role>' . PHP_EOL;
200
            $xmlContent .= '    <name>' . htmlspecialchars($roleName) . '</name>' . PHP_EOL;
201
            $xmlContent .= '  </role>' . PHP_EOL;
202
        }
203
        $xmlContent .= '</roles>';
204
205
        file_put_contents($destinationDir . '/roles.xml', $xmlContent);
206
    }
207
208
    /**
209
     * Creates the calendar.xml file.
210
     */
211
    private function createCalendarXml(array $calendarData, string $destinationDir): void
212
    {
213
        $xmlContent = '<?xml version="1.0" encoding="UTF-8"?>' . PHP_EOL;
214
        $xmlContent .= '<calendar>' . PHP_EOL;
215
        foreach ($calendarData as $event) {
216
            $eventName = $event['name'] ?? 'Event';
217
            $timestart = $event['timestart'] ?? time();
218
            $duration = $event['duration'] ?? 3600;
219
220
            $xmlContent .= '  <event>' . PHP_EOL;
221
            $xmlContent .= '    <name>' . htmlspecialchars($eventName) . '</name>' . PHP_EOL;
222
            $xmlContent .= '    <timestart>' . $timestart . '</timestart>' . PHP_EOL;
223
            $xmlContent .= '    <duration>' . $duration . '</duration>' . PHP_EOL;
224
            $xmlContent .= '  </event>' . PHP_EOL;
225
        }
226
        $xmlContent .= '</calendar>';
227
228
        file_put_contents($destinationDir . '/calendar.xml', $xmlContent);
229
    }
230
231
    /**
232
     * Creates the comments.xml file.
233
     */
234
    private function createCommentsXml(array $commentsData, string $destinationDir): void
235
    {
236
        $xmlContent = '<?xml version="1.0" encoding="UTF-8"?>' . PHP_EOL;
237
        $xmlContent .= '<comments>' . PHP_EOL;
238
        foreach ($commentsData as $comment) {
239
            $content = $comment['content'] ?? 'No comment';
240
            $author = $comment['author'] ?? 'Anonymous';
241
242
            $xmlContent .= '  <comment>' . PHP_EOL;
243
            $xmlContent .= '    <content>' . htmlspecialchars($content) . '</content>' . PHP_EOL;
244
            $xmlContent .= '    <author>' . htmlspecialchars($author) . '</author>' . PHP_EOL;
245
            $xmlContent .= '  </comment>' . PHP_EOL;
246
        }
247
        $xmlContent .= '</comments>';
248
249
        file_put_contents($destinationDir . '/comments.xml', $xmlContent);
250
    }
251
252
    /**
253
     * Creates the competencies.xml file.
254
     */
255
    private function createCompetenciesXml(array $competenciesData, string $destinationDir): void
256
    {
257
        $xmlContent = '<?xml version="1.0" encoding="UTF-8"?>' . PHP_EOL;
258
        $xmlContent .= '<competencies>' . PHP_EOL;
259
        foreach ($competenciesData as $competency) {
260
            $name = $competency['name'] ?? 'Competency';
261
            $xmlContent .= '  <competency>' . PHP_EOL;
262
            $xmlContent .= '    <name>' . htmlspecialchars($name) . '</name>' . PHP_EOL;
263
            $xmlContent .= '  </competency>' . PHP_EOL;
264
        }
265
        $xmlContent .= '</competencies>';
266
267
        file_put_contents($destinationDir . '/competencies.xml', $xmlContent);
268
    }
269
270
    /**
271
     * Creates the completiondefaults.xml file.
272
     */
273
    private function createCompletionDefaultsXml(array $completionData, string $destinationDir): void
274
    {
275
        $xmlContent = '<?xml version="1.0" encoding="UTF-8"?>' . PHP_EOL;
276
        $xmlContent .= '<completiondefaults>' . PHP_EOL;
277
        foreach ($completionData as $completion) {
278
            $completionState = $completion['state'] ?? 0;
279
            $xmlContent .= '  <completion>' . PHP_EOL;
280
            $xmlContent .= '    <completionstate>' . $completionState . '</completionstate>' . PHP_EOL;
281
            $xmlContent .= '  </completion>' . PHP_EOL;
282
        }
283
        $xmlContent .= '</completiondefaults>';
284
285
        file_put_contents($destinationDir . '/completiondefaults.xml', $xmlContent);
286
    }
287
288
    /**
289
     * Creates the contentbank.xml file.
290
     */
291
    private function createContentBankXml(array $contentBankData, string $destinationDir): void
292
    {
293
        $xmlContent = '<?xml version="1.0" encoding="UTF-8"?>' . PHP_EOL;
294
        $xmlContent .= '<contentbank>' . PHP_EOL;
295
        foreach ($contentBankData as $content) {
296
            $id = $content['id'] ?? 0;
297
            $name = $content['name'] ?? 'Content';
298
            $xmlContent .= '  <content id="' . $id . '">' . htmlspecialchars($name) . '</content>' . PHP_EOL;
299
        }
300
        $xmlContent .= '</contentbank>';
301
302
        file_put_contents($destinationDir . '/contentbank.xml', $xmlContent);
303
    }
304
305
    /**
306
     * Creates the filters.xml file.
307
     */
308
    private function createFiltersXml(array $filtersData, string $destinationDir): void
309
    {
310
        $xmlContent = '<?xml version="1.0" encoding="UTF-8"?>' . PHP_EOL;
311
        $xmlContent .= '<filters>' . PHP_EOL;
312
        foreach ($filtersData as $filter) {
313
            $filterName = $filter['name'] ?? 'filter_example';
314
            $active = $filter['active'] ?? 1;
315
316
            $xmlContent .= '  <filter>' . PHP_EOL;
317
            $xmlContent .= '    <filtername>' . htmlspecialchars($filterName) . '</filtername>' . PHP_EOL;
318
            $xmlContent .= '    <active>' . $active . '</active>' . PHP_EOL;
319
            $xmlContent .= '  </filter>' . PHP_EOL;
320
        }
321
        $xmlContent .= '</filters>';
322
323
        file_put_contents($destinationDir . '/filters.xml', $xmlContent);
324
    }
325
}
326