ILIAS  release_6 Revision v6.24-5-g0c8bfefb3b8
All Data Structures Namespaces Files Functions Variables Modules Pages
ilSCORM13Package.php
Go to the documentation of this file.
1 <?php
2 
3 /* Copyright (c) 1998-2010 ILIAS open source, Extended GPL, see docs/LICENSE */
4 
11 require_once "./Modules/Scorm2004/classes/ilSCORM13Package.php";
12 require_once "./Modules/Scorm2004/classes/class.ilSCORM2004Chapter.php";
13 require_once "./Modules/Scorm2004/classes/class.ilSCORM2004Sco.php";
14 require_once "./Modules/Scorm2004/classes/class.ilSCORM2004PageNode.php";
15 require_once "./Modules/Scorm2004/classes/adlparser/SeqTreeBuilder.php";
16 require_once("./Modules/ScormAicc/classes/SCORM/class.ilSCORMTree.php");
17 
19 {
20  const DB_ENCODE_XSL = './Modules/Scorm2004/templates/xsl/op/op-scorm13.xsl';
21  const CONVERT_XSL = './Modules/Scorm2004/templates/xsl/op/scorm12To2004.xsl';
22  const DB_DECODE_XSL = './Modules/Scorm2004/templates/xsl/op/op-scorm13-revert.xsl';
23  const VALIDATE_XSD = './libs/ilias/Scorm2004/xsd/op/op-scorm13.xsd';
24 
25  const WRAPPER_HTML = './Modules/Scorm2004/scripts/converter/GenericRunTimeWrapper1.0_aadlc/GenericRunTimeWrapper.htm';
26  const WRAPPER_JS = './Modules/Scorm2004/scripts/converter/GenericRunTimeWrapper1.0_aadlc/SCOPlayerWrapper.js';
27 
28 
29  private $packageFile;
30  private $packageFolder;
31  private $packagesFolder;
32  private $packageData;
33  private $slm;
34  private $slm_tree;
35 
36  public $imsmanifest;
37  public $manifest;
38  public $diagnostic;
39  public $status;
40  public $packageId;
41  public $packageName;
42  public $packageHash;
43  public $userId;
44 
45  private $idmap = array();
46  private $progress = 0.0;
47 
48  private static $elements = array(
49  'cp' => array(
50  'manifest',
51  'organization',
52  'item',
53  'hideLMSUI',
54  'resource',
55  'file',
56  'dependency',
57  'sequencing',
58  'rule',
59  'auxilaryResource',
60  'condition',
61  'mapinfo',
62  'objective',
63  ),
64  'cmi' => array(
65  'comment',
66  'correct_response',
67  'interaction',
68  'node',
69  'objective',
70  ),
71  );
72 
73  public function __construct($packageId = null)
74  {
75  $this->packagesFolder = ''; // #25372
76  $this->load($packageId);
77  // $this->userId = $GLOBALS['DIC']['USER']['usr_id'];
78  }
79 
80  public function load($packageId)
81  {
82  global $DIC;
83  $ilDB = $DIC['ilDB'];
84 
85  if (!is_numeric($packageId)) {
86  return false;
87  }
88 
89  $lm_set = $ilDB->queryF('SELECT * FROM sahs_lm WHERE id = %s', array('integer'), array($packageId));
90  $lm_data = $ilDB->fetchAssoc($lm_set);
91  $pg_set = $ilDB->queryF('SELECT * FROM cp_package WHERE obj_id = %s', array('integer'), array($packageId));
92  $pg_data = $ilDB->fetchAssoc($lm_set);
93 
94  $this->packageData = array_merge($lm_data, $pg_data);
95  $this->packageId = $packageId;
96  $this->packageFolder = $this->packagesFolder . '/' . $packageId;
97  $this->packageFile = $this->packageFolder . '.zip';
98  $this->imsmanifestFile = $this->packageFolder . '/' . 'imsmanifest.xml';
99  return true;
100  }
101 
102  public function rollback()
103  {
104  $this->setProgress(0, 'Rolling back...');
105  $this->dbRemoveAll();
106  if (is_dir($this->packageFolder)) {
107  dir_delete($this->packageFolder);
108  }
109  if (is_file($this->packageFile)) {
110  @unlink($this->packageFile);
111  }
112  $this->setProgress(0, 'Roll back finished: Ok. ');
113  }
114 
115 
119  public function exportXML()
120  {
121  global $DIC;
122  $ilDB = $DIC['ilDB'];
123 
124  header('content-type: text/xml');
125  header('content-disposition: attachment; filename="manifest.xml"');
126 
127  $res = $ilDB->queryF(
128  'SELECT xmldata FROM cp_package WHERE obj_id = %s',
129  array('integer'),
130  array($this->packageId)
131  );
132  $row = $ilDB->fetchAssoc($res);
133 
134  print($row['xmldata']);
135  }
136 
137 
144  public function il_import($packageFolder, $packageId, $ilias, $validate, $reimport = false)
145  {
146  global $DIC;
147  $ilDB = $DIC['ilDB'];
148  $ilLog = $DIC['ilLog'];
149  $ilErr = $DIC['ilErr'];
150 
151  $title = "";
152 
153  if ($reimport === true) {
154  $this->packageId = $packageId;
155  $this->dbRemoveAll();
156  }
157 
158  $this->packageFolder = $packageFolder;
159  $this->packageId = $packageId;
160  $this->imsmanifestFile = $this->packageFolder . '/' . 'imsmanifest.xml';
161  //step 1 - parse Manifest-File and validate
162  $this->imsmanifest = new DOMDocument;
163  $this->imsmanifest->async = false;
164  if (!@$this->imsmanifest->load($this->imsmanifestFile)) {
165  $this->diagnostic[] = 'XML not wellformed';
166  return false;
167  }
168 
169  //step 2 tranform
170  $this->manifest = $this->transform($this->imsmanifest, self::DB_ENCODE_XSL);
171 
172  if (!$this->manifest) {
173  $this->diagnostic[] = 'Cannot transform into normalized manifest';
174  return false;
175  }
176  //setp 2.5 if only a single item, make sure the scormType of it's linked resource is SCO
177  $path = new DOMXpath($this->manifest);
178  $path->registerNamespace("scorm", "http://www.openpalms.net/scorm/scorm13");
179  $items = $path->query("//scorm:item");
180  if ($items->length == 1) {
181  $n = $items->item(0);
182  $resource = $path->query("//scorm:resource");//[&id='"+$n->getAttribute("resourceId")+"']");
183  foreach ($resource as $res) {
184  if ($res->getAttribute('id') == $n->getAttribute("resourceId")) {
185  $res->setAttribute('scormType', 'sco');
186  }
187  }
188  }
189  //$this->manifest->save("C:\Users\gratat\after.xml");
190  //step 3 validation -just for normalized XML
191  if ($validate == "y") {
192  if (!$this->validate($this->manifest, self::VALIDATE_XSD)) {
193  $ilErr->raiseError(
194  "<b>The uploaded SCORM 1.2 / SCORM 2004 is not valid. You can try to import the package without the validation option checked on your own risk. </b><br><br>Validation Error(s):</b><br> Normalized XML is not conform to " . self::VALIDATE_XSD,
195  $ilErr->MESSAGE
196  );
197  }
198  }
199  $this->dbImport($this->manifest);
200 
201  if (file_exists($this->packageFolder . '/' . 'index.xml')) {
202  $doc = simplexml_load_file($this->packageFolder . '/' . 'index.xml');
203  $l = $doc->xpath("/ContentObject/MetaData");
204  if ($l[0]) {
205  include_once 'Services/MetaData/classes/class.ilMDXMLCopier.php';
206  $mdxml = new ilMDXMLCopier($l[0]->asXML(), $packageId, $packageId, ilObject::_lookupType($packageId));
207  $mdxml->startParsing();
208  $mdxml->getMDObject()->update();
209  }
210  } else {
211  include_once("./Modules/Scorm2004/classes/class.ilSCORM13MDImporter.php");
212  $importer = new ilSCORM13MDImporter($this->imsmanifest, $packageId);
213  $importer->import();
214  $title = $importer->getTitle();
215  $description = $importer->getDescription();
216  if ($description != "") {
218  }
219  }
220 
221  //step 5
222  $x = simplexml_load_string($this->manifest->saveXML());
223  $x['persistPreviousAttempts'] = $this->packageData['persistprevattempts'];
224  // $x['online'] = !$this->getOfflineStatus();//$this->packageData['c_online'];
225 
226  $x['defaultLessonMode'] = $this->packageData['default_lesson_mode'];
227  $x['credit'] = $this->packageData['credit'];
228  $x['autoReview'] = $this->packageData['auto_review'];
229  $j = array();
230  // first read resources into flat array to resolve item/identifierref later
231  $r = array();
232  foreach ($x->resource as $xe) {
233  $r[strval($xe['id'])] = $xe;
234  unset($xe);
235  }
236  // iterate through items and set href and scoType as activity attributes
237  foreach ($x->xpath('//*[local-name()="item"]') as $xe) {
238  // get reference to resource and set href accordingly
239  if ($b = $r[strval($xe['resourceId'])]) {
240  $xe['href'] = strval($b['base']) . strval($b['href']);
241  unset($xe['resourceId']);
242  if (strval($b['scormType']) == 'sco') {
243  $xe['sco'] = true;
244  }
245  }
246  }
247  // iterate recursivly through activities and build up simple php object
248  // with items and associated sequencings
249  // top node is the default organization which is handled as an item
250  self::jsonNode($x->organization, $j['item']);
251  foreach ($x->sequencing as $s) {
252  self::jsonNode($s, $j['sequencing'][]);
253  }
254  // combined manifest+resources xml:base is set as organization base
255  $j['item']['base'] = strval($x['base']);
256  // package folder is base to whole playing process
257  $j['base'] = $packageFolder . '/';
258  $j['foreignId'] = floatval($x['foreignId']); // manifest cp_node_id for associating global (package wide) objectives
259  $j['id'] = strval($x['id']); // manifest id for associating global (package wide) objectives
260 
261 
262  //last step - build ADL Activity tree
263  $act = new SeqTreeBuilder();
264  $adl_tree = $act->buildNodeSeqTree($this->imsmanifestFile);
265  $ilDB->update(
266  'cp_package',
267  array(
268  'xmldata' => array('clob', $x->asXML()),
269  'jsdata' => array('clob', json_encode($j)),
270  'activitytree' => array('clob', json_encode($adl_tree['tree'])),
271  'global_to_system' => array('integer', (int) $adl_tree['global']),
272  'shared_data_global_to_system' => array('integer', (int) $adl_tree['dataglobal'])
273  ),
274  array(
275  'obj_id' => array('integer', (int) $this->packageId)
276  )
277  );
278 
279  // title retrieved by importer
280  if ($title != "") {
281  return $title;
282  }
283 
284  return $j['item']['title'];
285  }
286 
287 
294  public function il_importSco($packageId, $sco_id, $packageFolder)
295  {
296  global $DIC;
297  $ilDB = $DIC['ilDB'];
298  $ilLog = $DIC['ilLog'];
299 
300  $this->packageFolder = $packageFolder;
301  $this->packageId = $packageId;
302  $this->imsmanifestFile = $this->packageFolder . '/' . 'index.xml';
303  $this->imsmanifest = new DOMDocument;
304  $this->imsmanifest->async = false;
305 
306  if (!@$this->imsmanifest->load($this->imsmanifestFile)) {
307  $this->diagnostic[] = 'XML not wellformed';
308  return false;
309  }
310 
312  $sco = new ilSCORM2004Sco($slm, $sco_id);
313  $this->dbImportSco($slm, $sco);
314 
315  // import sco.xml
316  $sco_xml_file = $this->packageFolder . '/sco.xml';
317  if (is_file($sco_xml_file)) {
318  $scodoc = new DOMDocument;
319  $scodoc->async = false;
320  if (!@$scodoc->load($sco_xml_file)) {
321  $this->diagnostic[] = 'XML of sco.xml not wellformed';
322  return false;
323  }
324  //$doc = new SimpleXMLElement($scodoc->saveXml());
325  //$l = $doc->xpath("/sco/objective");
326  $xpath = new DOMXPath($scodoc);
327  $nodes = $xpath->query("/sco/objective");
328  foreach ($nodes as $node) {
329  $t_node = $node->firstChild;
330  if (is_object($t_node)) {
331  $objective_text = $t_node->textContent;
332  if (trim($objective_text) != "") {
333  $objs = $sco->getObjectives();
334  foreach ($objs as $o) {
335  $mappings = $o->getMappings();
336  if ($mappings == null) {
337  $ob = new ilScorm2004Objective($sco->getId(), $o->getId());
338  $ob->setObjectiveID($objective_text);
339  $ob->updateObjective();
340  }
341  }
342  }
343  }
344  }
345  }
346  return "";
347  }
348 
355  public function il_importAss($packageId, $sco_id, $packageFolder)
356  {
357  global $DIC;
358  $ilDB = $DIC['ilDB'];
359  $ilLog = $DIC['ilLog'];
360 
361  $this->packageFolder = $packageFolder;
362  $this->packageId = $packageId;
363  $this->imsmanifestFile = $this->packageFolder . '/' . 'index.xml';
364  $this->imsmanifest = new DOMDocument;
365  $this->imsmanifest->async = false;
366 
367  if (!@$this->imsmanifest->load($this->imsmanifestFile)) {
368  $this->diagnostic[] = 'XML not wellformed';
369  return false;
370  }
371 
373  $sco = new ilSCORM2004Asset($slm, $sco_id);
374  $this->dbImportSco($slm, $sco, true);
375 
376  // import sco.xml
377  /*
378  $sco_xml_file = $this->packageFolder . '/sco.xml';
379  if (is_file($sco_xml_file))
380  {
381  $scodoc = new DOMDocument;
382  $scodoc->async = false;
383  if (!@$scodoc->load($sco_xml_file))
384  {
385  $this->diagnostic[] = 'XML of sco.xml not wellformed';
386  return false;
387  }
388  //$doc = new SimpleXMLElement($scodoc->saveXml());
389  //$l = $doc->xpath("/sco/objective");
390  $xpath = new DOMXPath($scodoc);
391  $nodes = $xpath->query("/sco/objective");
392  foreach($nodes as $node)
393  {
394  $t_node = $node->firstChild;
395  if (is_object($t_node))
396  {
397  $objective_text = $t_node->textContent;
398  if (trim($objective_text) != "")
399  {
400  $objs = $sco->getObjectives();
401  foreach ($objs as $o)
402  {
403  $mappings = $o->getMappings();
404  if ($mappings == null)
405  {
406  $ob = new ilScorm2004Objective($sco->getId(), $o->getId());
407  $ob->setObjectiveID($objective_text);
408  $ob->updateObjective();
409  }
410  }
411  }
412  }
413  }
414  }
415  */
416  return "";
417  }
418 
419  public function il_importLM($slm, $packageFolder, $a_import_sequencing = false)
420  {
421  global $DIC;
422  $ilDB = $DIC['ilDB'];
423  $ilLog = $DIC['ilLog'];
424 
425  $this->packageFolder = $packageFolder;
426  $this->packageId = $slm->getId();
427  $this->imsmanifestFile = $this->packageFolder . '/' . 'imsmanifest.xml';
428  $this->imsmanifest = new DOMDocument;
429  $this->imsmanifest->async = false;
430  $this->imsmanifest->formatOutput = false;
431  $this->imsmanifest->preserveWhiteSpace = false;
432  $this->slm = $slm;
433  if (!@$this->imsmanifest->load($this->imsmanifestFile)) {
434  $this->diagnostic[] = 'XML not wellformed';
435  return false;
436  }
437 
438  $this->mani_xpath = new DOMXPath($this->imsmanifest);
439  $this->mani_xpath->registerNamespace("d", "http://www.imsproject.org/xsd/imscp_rootv1p1p2");
440  $this->mani_xpath->registerNamespace("imscp", "http://www.imsglobal.org/xsd/imscp_v1p1");
441  $this->mani_xpath->registerNamespace("imsss", "http://www.imsglobal.org/xsd/imsss");
442 
443 
444  $this->dbImportLM(
445  simplexml_import_dom($this->imsmanifest->documentElement),
446  "",
447  $a_import_sequencing
448  );
449 
450  if (is_dir($packageFolder . "/glossary")) {
451  $this->importGlossary($slm, $packageFolder . "/glossary");
452  }
453  //die($slm->title);
454 
455  return $slm->title;
456  }
457 
459  {
460  // create and insert object in objecttree
461  $newObj = new ilObjGlossary();
462  $newObj->setType('glo');
463  $newObj->setTitle('');
464  $newObj->create(true);
465  $newObj->createReference();
466  $newObj->putInTree($_GET["ref_id"]);
467  $newObj->setPermissions($_GET["ref_id"]);
468 
469  $xml_file = $packageFolder . "/glossary.xml";
470 
471  // check whether xml file exists within zip file
472  if (!is_file($xml_file)) {
473  return;
474  }
475 
476  include_once("./Modules/LearningModule/classes/class.ilContObjParser.php");
477  $contParser = new ilContObjParser($newObj, $xml_file, $packageFolder);
478  $contParser->startParsing();
479  $newObj->update();
480  //ilObject::_writeImportId($newObj->getId(), $newObj->getImportId());
481  $slm->setAssignedGlossary($newObj->getId());
482  $slm->update();
483  }
484 
485  public function dbImportLM($node, $parent_id = "", $a_import_sequencing = false)
486  {
487  switch ($node->getName()) {
488  case "manifest":
489  $this->slm_tree = new ilTree($this->slm->getId());
490  $this->slm_tree->setTreeTablePK("slm_id");
491  $this->slm_tree->setTableNames('sahs_sc13_tree', 'sahs_sc13_tree_node');
492  $this->slm_tree->addTree($this->slm->getId(), 1);
493 
494  //add seqinfo for rootNode
495  include_once("./Modules/Scorm2004/classes/seq_editor/class.ilSCORM2004Sequencing.php");
496  $seq_info = new ilSCORM2004Sequencing($this->slm->getId(), true);
497 
498  // get original sequencing information
499  $r = $this->mani_xpath->query("/d:manifest/d:organizations/d:organization/imsss:sequencing");
500  $this->imsmanifest->formatOutput = false;
501  if ($r) {
502  $this->setSequencingInfo($r->item(0), $seq_info, $a_import_sequencing);
503  if ($a_import_sequencing) {
504  $seq_info->initDom();
505  }
506  }
507  $seq_info->insert();
508 
509  if (file_exists($this->packageFolder . '/' . 'index.xml')) {
510  $doc = simplexml_load_file($this->packageFolder . '/' . 'index.xml');
511  $l = $doc->xpath("/ContentObject/MetaData");
512  if ($l[0]) {
513  include_once 'Services/MetaData/classes/class.ilMDXMLCopier.php';
514  $mdxml = new ilMDXMLCopier($l[0]->asXML(), $this->slm->getId(), $this->slm->getId(), $this->slm->getType());
515  $mdxml->startParsing();
516  $mdxml->getMDObject()->update();
517  }
518  }
519  break;
520  case "organization":
521  $this->slm->title = $node->title;
522  break;
523  case "item":
524  $a = $node->attributes();
525  if (preg_match("/il_\d+_chap_\d+/", $a['identifier'])) {
526  $chap = new ilSCORM2004Chapter($this->slm);
527  $chap->setTitle($node->title);
528  $chap->setSLMId($this->slm->getId());
529  $chap->create(true);
530 
531  // save sequencing information
532  $r = $this->mani_xpath->query("//d:item[@identifier='" . $a['identifier'] . "']/imsss:sequencing");
533  if ($r) {
534  $seq_info = new ilSCORM2004Sequencing($chap->getId());
535  $this->setSequencingInfo($r->item(0), $seq_info, $a_import_sequencing);
536  $seq_info->initDom();
537  $seq_info->insert();
538  }
539 
540  ilSCORM2004Node::putInTree($chap, $parent_id, "");
541  $parent_id = $chap->getId();
542  $doc = simplexml_load_file($this->packageFolder . '/' . 'index.xml');
543  $l = $doc->xpath("/ContentObject/StructureObject/MetaData[General/Identifier/@Entry='" . $a['identifier'] . "']");
544  if ($l[0]) {
545  include_once 'Services/MetaData/classes/class.ilMDXMLCopier.php';
546  $mdxml = new ilMDXMLCopier($l[0]->asXML(), $this->slm->getId(), $chap->getId(), $chap->getType());
547  $mdxml->startParsing();
548  $mdxml->getMDObject()->update();
549  }
550  }
551  if (preg_match("/il_\d+_sco_(\d+)/", $a['identifier'], $match)) {
552  $sco = new ilSCORM2004Sco($this->slm);
553  $sco->setTitle($node->title);
554  $sco->setSLMId($this->slm->getId());
555  $sco->create(true);
556 
557  // save sequencing information
558  $r = $this->mani_xpath->query("//d:item[@identifier='" . $a['identifier'] . "']/imsss:sequencing");
559  if ($r) {
560  $seq_info = new ilSCORM2004Sequencing($sco->getId());
561  $this->setSequencingInfo(
562  $r->item(0),
563  $seq_info,
564  $a_import_sequencing,
565  "local_obj_" . $sco->getID() . "_0"
566  );
567  $seq_info->initDom();
568  $seq_info->insert();
569  }
570 
571  ilSCORM2004Node::putInTree($sco, $parent_id, "");
572  $newPack = new ilSCORM13Package();
573  $newPack->il_importSco($this->slm->getId(), $sco->getId(), $this->packageFolder . "/" . $match[1]);
574  $parent_id = $sco->getId();
575  }
576  if (preg_match("/il_\d+_ass_(\d+)/", $a['identifier'], $match)) {
577  $ass = new ilSCORM2004Asset($this->slm);
578  $ass->setTitle($node->title);
579  $ass->setSLMId($this->slm->getId());
580  $ass->create(true);
581 
582  // save sequencing information
583  $r = $this->mani_xpath->query("//d:item[@identifier='" . $a['identifier'] . "']/imsss:sequencing");
584  if ($r) {
585  $seq_info = new ilSCORM2004Sequencing($ass->getId());
586  $this->setSequencingInfo(
587  $r->item(0),
588  $seq_info,
589  $a_import_sequencing,
590  "local_obj_" . $ass->getID() . "_0"
591  );
592  $seq_info->initDom();
593  $seq_info->insert();
594  }
595 
596  ilSCORM2004Node::putInTree($ass, $parent_id, "");
597  $newPack = new ilSCORM13Package();
598  $newPack->il_importAss($this->slm->getId(), $ass->getId(), $this->packageFolder . "/" . $match[1]);
599  $parent_id = $ass->getId();
600  }
601 
602  break;
603  }
604  //if($node->nodeType==XML_ELEMENT_NODE)
605  {
606  foreach ($node->children() as $child) {
607  $this->dbImportLM($child, $parent_id, $a_import_sequencing);
608  }
609  }
610  }
611 
618  public function setSequencingInfo($a_node, $a_seq_info, $a_import_sequencing, $a_fix_obj_id = "")
619  {
620  $seq_xml = trim(str_replace("imsss:", "", $this->imsmanifest->saveXML($a_node)));
621  if ($seq_xml != "") {
622  $a_seq_info->setImportSeqXml('<?xml version="1.0"?>' . $seq_xml);
623  }
624  if ($a_import_sequencing) {
625  if ($a_fix_obj_id != "") {
626  $seq_xml = preg_replace("/local_obj_[0-9]*_0/", $a_fix_obj_id, $seq_xml);
627  }
628  $a_seq_info->setSeqXml('<?xml version="1.0"?>' . $seq_xml);
629  }
630  }
631 
632 
633  private function setProgress($progress, $msg = '')
634  {
635  $this->progress = $progress;
636  $this->diagnostic[] = $msg;
637  }
638 
647  public function jsonNode($node, &$sink)
648  {
649  foreach ($node->attributes() as $k => $v) {
650  // cast to boolean and number if possible
651  $v = strval($v);
652  if ($v === "true") {
653  $v = true;
654  } elseif ($v === "false") {
655  $v = false;
656  } elseif (is_numeric($v)) {
657  $v = (float) $v;
658  }
659  $sink[$k] = $v;
660  }
661  foreach ($node->children() as $name => $child) {
662  self::jsonNode($child, $sink[$name][]); // RECURSION
663  }
664  }
665 
666  public function dbImportSco($slm, $sco, $asset = false)
667  {
668  $qtis = array();
669  $d = ilUtil::getDir($this->packageFolder);
670  foreach ($d as $f) {
671  //continue;
672  if ($f["type"] == 'file' && substr($f["entry"], 0, 4) == 'qti_') {
673  $qtiParser = new ilQTIParser($this->packageFolder . "/" . $f["entry"], IL_MO_VERIFY_QTI, 0, "");
674  $result = $qtiParser->startParsing();
675  $founditems = &$qtiParser->getFoundItems();
676  // die(print_r($founditems));
677  foreach ($founditems as $qp) {
678  $newObj = new ilObjTest(0, true);
679 
680  // This creates a lot of invalid repository objects for each question
681  // question are not repository objects (see e.g. table object_data), alex 29 Sep 2009
682 
683  // $newObj->setType ( $qp ['type'] );
684  // $newObj->setTitle ( $qp ['title'] );
685  // $newObj->create ( true );
686  // $newObj->createReference ();
687  // $newObj->putInTree ($_GET ["ref_id"]);
688  // $newObj->setPermissions ( $sco->getId ());
689  // $newObj->notify ("new", $_GET["ref_id"], $sco->getId (), $_GET["ref_id"], $newObj->getRefId () );
690  // $newObj->mark_schema->flush ();
691  $qtiParser = new ilQTIParser($this->packageFolder . "/" . $f["entry"], IL_MO_PARSE_QTI, 0, "");
692  $qtiParser->setTestObject($newObj);
693  $result = $qtiParser->startParsing();
694  // $newObj->saveToDb ();
695  $qtis = array_merge($qtis, $qtiParser->getImportMapping());
696  }
697  }
698  }
699  //exit;
700  include_once 'Modules/Scorm2004/classes/class.ilSCORM2004Page.php';
701  $doc = new SimpleXMLElement($this->imsmanifest->saveXml());
702  $l = $doc->xpath("/ContentObject/MetaData");
703  if ($l[0]) {
704  include_once 'Services/MetaData/classes/class.ilMDXMLCopier.php';
705  $mdxml = new ilMDXMLCopier($l[0]->asXML(), $slm->getId(), $sco->getId(), $sco->getType());
706  $mdxml->startParsing();
707  $mdxml->getMDObject()->update();
708  }
709  $l = $doc->xpath("/ContentObject/PageObject");
710  foreach ($l as $page_xml) {
711  $tnode = $page_xml->xpath('MetaData/General/Title');
712  $page = new ilSCORM2004PageNode($slm);
713  $page->setTitle($tnode [0]);
714  $page->setSLMId($slm->getId());
715  $page->create(true);
716  // ilSCORM2004Node::putInTree ( $page, $sco->getId (), $target );
717  ilSCORM2004Node::putInTree($page, $sco->getId(), "");
718  $pmd = $page_xml->xpath("MetaData");
719  if ($pmd[0]) {
720  include_once 'Services/MetaData/classes/class.ilMDXMLCopier.php';
721  $mdxml = new ilMDXMLCopier($pmd[0]->asXML(), $slm->getId(), $page->getId(), $page->getType());
722  $mdxml->startParsing();
723  $mdxml->getMDObject()->update();
724  }
725  $tnode = $page_xml->xpath("//MediaObject/MediaAlias | //InteractiveImage/MediaAlias");
726  foreach ($tnode as $ttnode) {
727  include_once './Services/MediaObjects/classes/class.ilObjMediaObject.php';
728  $OriginId = $ttnode["OriginId"];
729  $medianodes = $doc->xpath("//MediaObject[MetaData/General/Identifier/@Entry='" . $OriginId . "']");
730  $medianode = $medianodes[0];
731  if ($medianode) {
732  $media_object = new ilObjMediaObject();
733  $media_object->setTitle($medianode->MetaData->General->Title);
734  $media_object->setDescription($medianode->MetaData->General->Description);
735  $media_object->create(false);
736  $mmd = $medianode->xpath("MetaData");
737  if ($mmd[0]) {
738  include_once 'Services/MetaData/classes/class.ilMDXMLCopier.php';
739  $mdxml = new ilMDXMLCopier($mmd[0]->asXML(), 0, $media_object->getId(), $media_object->getType());
740  $mdxml->startParsing();
741  $mdxml->getMDObject()->update();
742  }
743  // determine and create mob directory, move uploaded file to directory
744  $media_object->createDirectory();
745  $mob_dir = ilObjMediaObject::_getDirectory($media_object->getId());
746  foreach ($medianode->MediaItem as $xMediaItem) {
747  $media_item = new ilMediaItem();
748  $media_object->addMediaItem($media_item);
749  $media_item->setPurpose($xMediaItem["Purpose"]);
750  $media_item->setFormat($xMediaItem->Format);
751  $media_item->setLocation($xMediaItem->Location);
752  $media_item->setLocationType($xMediaItem->Location["Type"]);
753  $media_item->setWidth($xMediaItem->Layout["Width"]);
754  $media_item->setHeight($xMediaItem->Layout["Height"]);
755  $media_item->setHAlign($xMediaItem->Layout["HorizontalAlign"]);
756  $media_item->setCaption($xMediaItem->Caption);
757  $media_item->setTextRepresentation($xMediaItem->TextRepresentation);
758  $nr = 0;
759 
760  // add map areas (external links only)
761  foreach ($xMediaItem->MapArea as $n => $v) {
762  if ($v->ExtLink["Href"] != "") {
763  $ma = new ilMapArea();
764 
765  $map_area = new ilMapArea();
766  $map_area->setShape($v["Shape"]);
767  $map_area->setCoords($v["Coords"]);
768  $map_area->setLinkType(IL_EXT_LINK);
769  $map_area->setTitle($v->ExtLink);
770  $map_area->setHref($v->ExtLink["Href"]);
771 
772  $media_item->addMapArea($map_area);
773  }
774  }
775 
776  if ($media_item->getLocationType() == "LocalFile") {
777  // $tmp_name = $this->packageFolder."/objects/".$OriginId."/".$xMediaItem->Location;
778 // copy($tmp_name, $mob_dir."/".$xMediaItem->Location);
779  }
780  }
781 
782  // copy whole directory
783  ilUtil::rCopy($this->packageFolder . "/objects/" . $OriginId, $mob_dir);
784 
785 
786  // alex: fixed media import: these lines have been
787  // behind the next curly bracket which makes it fail
788  // when no medianode is given. (id=0 -> fatal error)
789  ilUtil::renameExecutables($mob_dir);
790  $media_object->update(true);
791  $ttnode ["OriginId"] = "il__mob_" . $media_object->getId();
792  }
793  }
794  include_once("./Modules/File/classes/class.ilObjFile.php");
795  include_once("./Services/Utilities/classes/class.ilFileUtils.php");
796  include_once("./Services/MediaObjects/classes/class.ilObjMediaObject.php");
797 
798  $intlinks = $page_xml->xpath("//IntLink");
799  //die($intlinks);
800  //if($intlinks )
801  {
802  foreach ($intlinks as $intlink) {
803  if ($intlink["Type"] != "File") {
804  continue;
805  }
806  $path = $this->packageFolder . "/objects/" . str_replace('dfile', 'file', $intlink["Target"]);
807  if (!is_dir($path)) {
808  continue;
809  }
810  $ffiles = array();
811  ilFileUtils::recursive_dirscan($path, $ffiles);
812  $filename = $ffiles["file"][0];
813  $fileObj = new ilObjFile();
814  $fileObj->setType("file");
817 
818  // better use this, mime_content_type is deprecated
819  $fileObj->setFileType(ilObjMediaObject::getMimeType($path . "/" . $filename));
820 
821  $fileObj->setFileSize(filesize($path . "/" . $filename));
822  $fileObj->create();
823  $fileObj->createReference();
824  //$fileObj->putInTree($_GET["ref_id"]);
825  //$fileObj->setPermissions($slm->getId ());
826  $fileObj->createDirectory();
827  $fileObj->storeUnzipedFile($path . "/" . $filename, ilFileUtils::utf8_encode(ilUtil::stripSlashes($filename)));
828  $intlink["Target"] = "il__dfile_" . $fileObj->getId();
829  }
830  }
831  $fileitems = $page_xml->xpath("//FileItem/Identifier");
832  //if($intlinks )
833  {
834  foreach ($fileitems as $fileitem) {
835  $path = $this->packageFolder . "/objects/" . $fileitem["Entry"];
836  if (!is_dir($path)) {
837  continue;
838  }
839  $ffiles = array();
840  ilFileUtils::recursive_dirscan($path, $ffiles);
841  $filename = $ffiles["file"][0];
842  $fileObj = new ilObjFile();
843  $fileObj->setType("file");
846 
847  // better use this, mime_content_type is deprecated
848  $fileObj->setFileType(ilObjMediaObject::getMimeType($path . "/" . $filename));
849 
850  $fileObj->setFileSize(filesize($path . "/" . $filename));
851  $fileObj->create();
852  $fileObj->createReference();
853  //$fileObj->putInTree($_GET["ref_id"]);
854  //$fileObj->setPermissions($slm->getId ());
855  $fileObj->createDirectory();
856  $fileObj->storeUnzipedFile($path . "/" . $filename, ilFileUtils::utf8_encode(ilUtil::stripSlashes($filename)));
857  $fileitem["Entry"] = "il__file_" . $fileObj->getId();
858  }
859  }
860  $pagex = new ilSCORM2004Page($page->getId());
861 
862  $ddoc = new DOMDocument();
863  $ddoc->async = false;
864  $ddoc->preserveWhiteSpace = false;
865  $ddoc->formatOutput = false;
866  $ddoc->loadXML($page_xml->asXML());
867  $xpath = new DOMXPath($ddoc);
868  $tnode = $xpath->query('PageContent');
869  $t = "<PageObject>";
870  foreach ($tnode as $ttnode) {
871  $t .= str_replace("&amp;", "&", $ddoc->saveXML($ttnode));
872  }
873  $t .= "</PageObject>";
874  foreach ($qtis as $old => $q) {
875  $t = str_replace($old, 'il__qst_' . $q['pool'], $t);
876  }
877  $pagex->setXMLContent($t);
878  $pagex->updateFromXML();
879  }
880  }
881 
882  public function dbImport($node, &$lft = 1, $depth = 1, $parent = 0)
883  {
884  global $DIC;
885  $ilDB = $DIC['ilDB'];
886 
887  switch ($node->nodeType) {
888  case XML_DOCUMENT_NODE:
889 
890  // insert into cp_package
891 
892  $res = $ilDB->queryF(
893  'SELECT * FROM cp_package WHERE obj_id = %s AND c_identifier = %s',
894  array('integer', 'text'),
895  array($this->packageId, $this->packageName)
896  );
897  if ($num_rows = $ilDB->numRows($res)) {
898  $query = 'UPDATE cp_package '
899  . 'SET persistprevattempts = %s, c_settings = %s '
900  . 'WHERE obj_id = %s AND c_identifier= %s';
901  $ilDB->manipulateF(
902  $query,
903  array('integer', 'text', 'integer', 'text'),
904  array(0, null, $this->packageId, $this->packageName)
905  );
906  } else {
907  $query = 'INSERT INTO cp_package (obj_id, c_identifier, persistprevattempts, c_settings) '
908  . 'VALUES (%s, %s, %s, %s)';
909  $ilDB->manipulateF(
910  $query,
911  array('integer','text','integer', 'text'),
912  array($this->packageId, $this->packageName, 0, null)
913  );
914  }
915 
916  // run sub nodes
917  $this->dbImport($node->documentElement); // RECURSION
918  break;
919 
920  case XML_ELEMENT_NODE:
921  if ($node->nodeName === 'manifest') {
922  if ($node->getAttribute('uri') == "") {
923  // default URI is md5 hash of zip file, i.e. packageHash
924  $node->setAttribute('uri', 'md5:' . $this->packageHash);
925  }
926  }
927 
928  $cp_node_id = $ilDB->nextId('cp_node');
929 
930  $query = 'INSERT INTO cp_node (cp_node_id, slm_id, nodename) '
931  . 'VALUES (%s, %s, %s)';
932  $ilDB->manipulateF(
933  $query,
934  array('integer', 'integer', 'text'),
935  array($cp_node_id, $this->packageId, $node->nodeName)
936  );
937 
938  $query = 'INSERT INTO cp_tree (child, depth, lft, obj_id, parent, rgt) '
939  . 'VALUES (%s, %s, %s, %s, %s, %s)';
940  $ilDB->manipulateF(
941  $query,
942  array('integer', 'integer', 'integer', 'integer', 'integer', 'integer'),
943  array($cp_node_id, $depth, $lft++, $this->packageId, $parent, 0)
944  );
945 
946  // insert into cp_*
947  //$a = array('cp_node_id' => $cp_node_id);
948  $names = array('cp_node_id');
949  $values = array($cp_node_id);
950  $types = array('integer');
951 
952  foreach ($node->attributes as $attr) {
953  switch (strtolower($attr->name)) {
954  case 'completionsetbycontent': $names[] = 'completionbycontent';break;
955  case 'objectivesetbycontent': $names[] = 'objectivebycontent';break;
956  case 'type': $names[] = 'c_type';break;
957  case 'mode': $names[] = 'c_mode';break;
958  case 'language': $names[] = 'c_language';break;
959  case 'condition': $names[] = 'c_condition';break;
960  case 'operator': $names[] = 'c_operator';break;
961  case 'condition': $names[] = 'c_condition';break;
962  case 'readnormalizedmeasure': $names[] = 'readnormalmeasure';break;
963  case 'writenormalizedmeasure': $names[] = 'writenormalmeasure';break;
964  case 'minnormalizedmeasure': $names[] = 'minnormalmeasure';break;
965  case 'primary': $names[] = 'c_primary';break;
966  case 'minnormalizedmeasure': $names[] = 'minnormalmeasure';break;
967  case 'persistpreviousattempts': $names[] = 'persistprevattempts';break;
968  case 'identifier': $names[] = 'c_identifier';break;
969  case 'settings': $names[] = 'c_settings';break;
970  case 'activityabsolutedurationlimit': $names[] = 'activityabsdurlimit';break;
971  case 'activityexperienceddurationlimit': $names[] = 'activityexpdurlimit';break;
972  case 'attemptabsolutedurationlimit': $names[] = 'attemptabsdurlimit';break;
973  case 'measuresatisfactionifactive': $names[] = 'measuresatisfactive';break;
974  case 'objectivemeasureweight': $names[] = 'objectivemeasweight';break;
975  case 'requiredforcompleted': $names[] = 'requiredcompleted';break;
976  case 'requiredforincomplete': $names[] = 'requiredincomplete';break;
977  case 'requiredfornotsatisfied': $names[] = 'requirednotsatisfied';break;
978  case 'rollupobjectivesatisfied': $names[] = 'rollupobjectivesatis';break;
979  case 'rollupprogresscompletion': $names[] = 'rollupprogcompletion';break;
980  case 'usecurrentattemptobjectiveinfo': $names[] = 'usecurattemptobjinfo';break;
981  case 'usecurrentattemptprogressinfo': $names[] = 'usecurattemptproginfo';break;
982  default: $names[] = strtolower($attr->name);break;
983  }
984 
985  if (in_array(
986  $names[count($names) - 1],
987  array('flow', 'completionbycontent',
988  'objectivebycontent', 'rollupobjectivesatis',
989  'tracked', 'choice',
990  'choiceexit', 'satisfiedbymeasure',
991  'c_primary', 'constrainchoice',
992  'forwardonly', 'global_to_system',
993  'writenormalmeasure', 'writesatisfiedstatus',
994  'readnormalmeasure', 'readsatisfiedstatus',
995  'preventactivation', 'measuresatisfactive',
996  'reorderchildren', 'usecurattemptproginfo',
997  'usecurattemptobjinfo', 'rollupprogcompletion',
998  'read_shared_data', 'write_shared_data',
999  'shared_data_global_to_system', 'completedbymeasure')
1000  )) {
1001  if ($attr->value == 'true') {
1002  $values[] = 1;
1003  } elseif ($attr->value == 'false') {
1004  $values[] = 0;
1005  } else {
1006  $values[] = (int) $attr->value;
1007  }
1008  } else {
1009  $values[] = $attr->value;
1010  }
1011 
1012  if (in_array(
1013  $names[count($names) - 1],
1014  array('objectivesglobtosys', 'attemptlimit',
1015  'flow', 'completionbycontent',
1016  'objectivebycontent', 'rollupobjectivesatis',
1017  'tracked', 'choice',
1018  'choiceexit', 'satisfiedbymeasure',
1019  'c_primary', 'constrainchoice',
1020  'forwardonly', 'global_to_system',
1021  'writenormalmeasure', 'writesatisfiedstatus',
1022  'readnormalmeasure', 'readsatisfiedstatus',
1023  'preventactivation', 'measuresatisfactive',
1024  'reorderchildren', 'usecurattemptproginfo',
1025  'usecurattemptobjinfo', 'rollupprogcompletion',
1026  'read_shared_data', 'write_shared_data',
1027  'shared_data_global_to_system')
1028  )) {
1029  $types[] = 'integer';
1030  } elseif (in_array(
1031  $names[count($names) - 1],
1032  array('jsdata', 'xmldata', 'activitytree', 'data')
1033  )) {
1034  $types[] = 'clob';
1035  } elseif (in_array(
1036  $names[count($names) - 1],
1037  array('objectivemeasweight')
1038  )) {
1039  $types[] = 'float';
1040  } else {
1041  $types[] = 'text';
1042  }
1043  }
1044 
1045  if ($node->nodeName === 'datamap') {
1046  $names[] = 'slm_id';
1047  $values[] = $this->packageId;
1048  $types[] = 'integer';
1049 
1050  $names[] = 'sco_node_id';
1051  $values[] = $parent;
1052  $types[] = 'integer';
1053  }
1054 
1055  // we have to change the insert method because of clob fields ($ilDB->manipulate does not work here)
1056  $insert_data = array();
1057  foreach ($names as $key => $db_field) {
1058  $insert_data[$db_field] = array($types[$key], trim($values[$key]));
1059  }
1060  $ilDB->insert('cp_' . strtolower($node->nodeName), $insert_data);
1061 
1062  $node->setAttribute('foreignId', $cp_node_id);
1063  $this->idmap[$node->getAttribute('id')] = $cp_node_id;
1064 
1065  // run sub nodes
1066  foreach ($node->childNodes as $child) {
1067  $this->dbImport($child, $lft, $depth + 1, $cp_node_id); // RECURSION
1068  }
1069 
1070  // update cp_tree (rgt value for pre order walk in sql tree)
1071  $query = 'UPDATE cp_tree SET rgt = %s WHERE child = %s';
1072  $ilDB->manipulateF(
1073  $query,
1074  array('integer', 'integer'),
1075  array($lft++, $cp_node_id)
1076  );
1077 
1078  break;
1079  }
1080  }
1081 
1082 
1083  public function removeCMIData()
1084  {
1085  include_once("./Modules/Scorm2004/classes/class.ilSCORM2004DeleteData.php");
1087 
1088  include_once("./Services/Tracking/classes/class.ilLPStatusWrapper.php");
1089  ilLPStatusWrapper::_refreshStatus($this->packageId);
1090  }
1091 
1092  public function removeCPData()
1093  {
1094  global $DIC;
1095  $ilDB = $DIC['ilDB'];
1096  $ilLog = $DIC['ilLog'];
1097 
1098  //get relevant nodes
1099  $cp_nodes = array();
1100 
1101  $res = $ilDB->queryF(
1102  'SELECT cp_node.cp_node_id FROM cp_node WHERE cp_node.slm_id = %s',
1103  array('integer'),
1104  array($this->packageId)
1105  );
1106  while ($data = $ilDB->fetchAssoc($res)) {
1107  $cp_nodes[] = $data['cp_node_id'];
1108  }
1109 
1110  //remove package data
1111  foreach (self::$elements['cp'] as $t) {
1112  $t = 'cp_' . $t;
1113 
1114  $in = $ilDB->in(strtolower($t) . '.cp_node_id', $cp_nodes, false, 'integer');
1115  $ilDB->manipulate('DELETE FROM ' . strtolower($t) . ' WHERE ' . $in);
1116  }
1117 
1118  // remove CP structure entries in tree and node
1119  $ilDB->manipulateF(
1120  'DELETE FROM cp_tree WHERE cp_tree.obj_id = %s',
1121  array('integer'),
1122  array($this->packageId)
1123  );
1124 
1125  $ilDB->manipulateF(
1126  'DELETE FROM cp_node WHERE cp_node.slm_id = %s',
1127  array('integer'),
1128  array($this->packageId)
1129  );
1130 
1131  // remove general package entry
1132  $ilDB->manipulateF(
1133  'DELETE FROM cp_package WHERE cp_package.obj_id = %s',
1134  array('integer'),
1135  array($this->packageId)
1136  );
1137  }
1138 
1139  public function dbRemoveAll()
1140  {
1141  //dont change order of calls
1142  $this->removeCMIData();
1143  $this->removeCPData();
1144  }
1145 
1146  public function transform($inputdoc, $xslfile, $outputpath = null)
1147  {
1148  $xsl = new DOMDocument;
1149  $xsl->async = false;
1150  if (!@$xsl->load($xslfile)) {
1151  die('ERROR: load StyleSheet ' . $xslfile);
1152  }
1153  $prc = new XSLTProcessor;
1154  $prc->registerPHPFunctions();
1155  $r = @$prc->importStyleSheet($xsl);
1156  if (false === @$prc->importStyleSheet($xsl)) {
1157  die('ERROR: importStyleSheet ' . $xslfile);
1158  }
1159  if ($outputpath) {
1160  file_put_contents($outputpath, $prc->transformToXML($inputdoc));
1161  } else {
1162  return $prc->transformToDoc($inputdoc);
1163  }
1164  }
1165 
1166  public function validate($doc, $schema)
1167  {
1168  libxml_use_internal_errors(true);
1169  $return = @$doc->schemaValidate($schema);
1170  if (!$return) {
1171  $levels = array(
1172  LIBXML_ERR_ERROR => 'Error',
1173  LIBXML_ERR_FATAL => 'Fatal Error'
1174  );
1175  foreach (libxml_get_errors() as $error) {
1176  $level = $levels[$error->level];
1177  if (isset($level)) {
1178  $message = trim($error->message);
1179  $this->diagnostic[] = "XSLT $level (Line $error->line) $message";
1180  }
1181  }
1182  libxml_clear_errors();
1183  }
1184  libxml_use_internal_errors(false);
1185  return $return;
1186  }
1187 
1188  //to be called from IlObjUser
1189  public static function _removeTrackingDataForUser($user_id)
1190  {
1191  include_once("./Modules/Scorm2004/classes/class.ilSCORM2004DeleteData.php");
1193  //missing updatestatus
1194  }
1195 }
Class ilSCORM2004PageNode.
dbImportSco($slm, $sco, $asset=false)
Content Object Parser.
static putInTree($a_obj, $a_parent_id="", $a_target_node_id="")
put this object into content object tree
static getMimeType($a_file, $a_external=null)
get mime type for file
Class ilSCORM2004Sco.
$data
Definition: storeScorm.php:23
dbImportLM($node, $parent_id="", $a_import_sequencing=false)
$result
transform($inputdoc, $xslfile, $outputpath=null)
jsonNode($node, &$sink)
Helper for UploadAndImport Recursively copies values from XML into PHP array for export as json Eleme...
dbImport($node, &$lft=1, $depth=1, $parent=0)
static rCopy($a_sdir, $a_tdir, $preserveTimeAttributes=false)
Copies content of a directory $a_sdir recursively to a directory $a_tdir.
startParsing()
stores xml data in array
$_GET["client_id"]
Class ilObjGlossary.
il_import($packageFolder, $packageId, $ilias, $validate, $reimport=false)
Imports an extracted SCORM 2004 module from ilias-data dir into database.
SCORM 13 Metadata importer.
static getDir($a_dir, $a_rec=false, $a_sub_dir="")
get directory
Class ilSCORM2004Chapter.
static _refreshStatus($a_obj_id, $a_users=null)
Set dirty.
static _getDirectory($a_mob_id)
Get absolute directory.
$ilErr
Definition: raiseError.php:18
setSequencingInfo($a_node, $a_seq_info, $a_import_sequencing, $a_fix_obj_id="")
Save sequencing ingo.
if($format !==null) $name
Definition: metadata.php:230
exportXML()
Export as internal XML.
foreach($_POST as $key=> $value) $res
il_importAss($packageId, $sco_id, $packageFolder)
Imports an extracted SCORM 2004 module from ilias-data dir into database.
const IL_MO_PARSE_QTI
Class ilSCORM2004Page.
setProgress($progress, $msg='')
Class ilMediaItem.
Class ilObjMediaObject.
static _removeTrackingDataForUser($user_id)
$query
$n
Definition: RandomTest.php:85
static stripSlashes($a_str, $a_strip_html=true, $a_allow="")
strip slashes if magic qoutes is enabled
il_importLM($slm, $packageFolder, $a_import_sequencing=false)
Class ilSCORM2004Sequencing.
static _lookupType($a_id, $a_reference=false)
lookup object type
$filename
Definition: buildRTE.php:89
static _writeDescription($a_obj_id, $a_desc)
write description to db (static)
if(php_sapi_name() !='cli') $in
Definition: Utf8Test.php:37
const IL_EXT_LINK
static utf8_encode($string)
utf8-encodes string if it is not a valid utf8-string.
Class ilMapArea.
validate($doc, $schema)
$lm_set
static renameExecutables($a_dir)
Rename uploaded executables for security reasons.
Class ilObjSCORM2004LearningModule.
__construct($packageId=null)
global $ilDB
Class ilSCORM2004Asset.
$DIC
Definition: xapitoken.php:46
$a
thx to https://mlocati.github.io/php-cs-fixer-configurator for the examples
il_importSco($packageId, $sco_id, $packageFolder)
Imports an extracted SCORM 2004 module from ilias-data dir into database.
$message
Definition: xapiexit.php:14
static recursive_dirscan($dir, &$arr)
Recursively scans a given directory and writes path and filename into referenced array.
const IL_MO_VERIFY_QTI
static removeCMIDataForPackage($packageId)
for($i=6; $i< 13; $i++) for($i=1; $i< 13; $i++) $d
Definition: date.php:296
importGlossary($slm, $packageFolder)