/**
  * Load a QTI_Item from an, RDF Item using the itemContent property of the
  * Item as the QTI xml
  *
  * @access public
  * @author Somsack Sipasseuth, <*****@*****.**>
  * @param  Resource item
  * @throws \common_Exception If $item is not representing an item with a QTI item model.
  * @return oat\taoQtiItem\model\qti\Item An item as a business object.
  */
 public function getDataItemByRdfItem(core_kernel_classes_Resource $item, $langCode = '', $resolveXInclude = false)
 {
     $returnValue = null;
     $itemService = taoItems_models_classes_ItemsService::singleton();
     //check if the item is QTI item
     if ($itemService->hasItemModel($item, array(ItemModel::MODEL_URI))) {
         //get the QTI xml
         $itemContent = $itemService->getItemContent($item, $langCode);
         if (!empty($itemContent)) {
             //Parse it and build the QTI_Data_Item
             $qtiParser = new Parser($itemContent);
             $returnValue = $qtiParser->load();
             if ($resolveXInclude && !empty($langCode)) {
                 //loadxinclude
                 $resolver = new ItemMediaResolver($item, $langCode);
                 $xincludeLoader = new XIncludeLoader($returnValue, $resolver);
                 $xincludeLoader->load(true);
             }
             if (!$returnValue->getAttributeValue('xml:lang')) {
                 $returnValue->setAttribute('xml:lang', \common_session_SessionManager::getSession()->getDataLanguage());
             }
         } else {
             // fail silently, since file might not have been created yet
             // $returnValue is then NULL.
             common_Logger::d('item(' . $item->getUri() . ') is empty, newly created?');
         }
     } else {
         throw new common_Exception('Non QTI item(' . $item->getUri() . ') opened via QTI Service');
     }
     return $returnValue;
 }
 /**
  * Load a QTI_Item from an, RDF Item using the itemContent property of the
  * Item as the QTI xml
  *
  * @access public
  * @author Somsack Sipasseuth, <*****@*****.**>
  * @param  Resource item
  * @throws \common_Exception If $item is not representing an item with a QTI item model.
  * @return Item An item as a business object.
  */
 public function getDataItemByRdfItem(core_kernel_classes_Resource $item, $langCode = '', $resolveXInclude = false)
 {
     $returnValue = null;
     try {
         //Parse it and build the QTI_Data_Item
         $file = $this->getXmlByRdfItem($item, $langCode);
         $qtiParser = new Parser($file);
         $returnValue = $qtiParser->load();
         if ($resolveXInclude && !empty($langCode)) {
             try {
                 //loadxinclude
                 $resolver = new ItemMediaResolver($item, $langCode);
                 $xincludeLoader = new XIncludeLoader($returnValue, $resolver);
                 $xincludeLoader->load(true);
             } catch (XIncludeException $exception) {
                 common_Logger::e($exception->getMessage());
             }
         }
         if (!$returnValue->getAttributeValue('xml:lang')) {
             $returnValue->setAttribute('xml:lang', \common_session_SessionManager::getSession()->getDataLanguage());
         }
     } catch (FileNotFoundException $e) {
         // fail silently, since file might not have been created yet
         // $returnValue is then NULL.
         common_Logger::d('item(' . $item->getUri() . ') is empty, newly created?');
     }
     return $returnValue;
 }
 /**
  * Test that xincludes are correctly loaded into pci elements
  */
 public function testLoadxincludeInPci()
 {
     $file = dirname(__FILE__) . '/samples/xml/qtiv2p1/xinclude/pci_include.xml';
     $href1 = 'stimulus.xml';
     $file1 = dirname(__FILE__) . '/samples/xml/qtiv2p1/xinclude/stimulus.xml';
     $mediaSource1 = $this->prophesize('oat\\taoMediaManager\\model\\MediaSource');
     $mediaSource1->download($href1)->willReturn($file1);
     $asset1 = $this->prophesize('oat\\tao\\model\\media\\MediaAsset');
     $asset1->getMediaSource()->willReturn($mediaSource1->reveal());
     $asset1->getMediaIdentifier()->willReturn($href1);
     $asset1Revealed = $asset1->reveal();
     $resolver = $this->prophesize('oat\\taoItems\\model\\media\\ItemMediaResolver');
     $resolver->resolve($href1)->willReturn($asset1Revealed);
     $this->assertEquals($file1, $asset1Revealed->getMediaSource()->download($asset1Revealed->getMediaIdentifier()));
     //load item model
     $qtiParser = new Parser($file);
     $item = $qtiParser->load();
     $this->assertTrue($item instanceof Item);
     //find the unique pci in the sample
     $pci = null;
     foreach ($item->getComposingElements() as $element) {
         if ($element instanceof PortableCustomInteraction) {
             $pci = $element;
             break;
         }
     }
     $this->assertNotNull($pci);
     //check inital markup
     $markupXml = simplexml_load_string($pci->getMarkup());
     $this->assertEquals(1, count($markupXml->xpath(".//*[name(.)='include']")), 'the pci markup has an include element');
     $this->assertEquals(0, count($markupXml->xpath(".//*[name(.)='img']")));
     $this->assertEquals(0, count($markupXml->xpath(".//*[name(.)='m:math']")));
     //load xinclude
     $xincludeLoader = new XIncludeLoader($item, $resolver->reveal());
     $xincludes = $xincludeLoader->load();
     //check markup after loading
     $markupXml = simplexml_load_string($pci->getMarkup());
     $this->assertEquals(1, count($xincludes));
     $this->assertEquals(0, count($markupXml->xpath(".//*[name(.)='include']")), 'the include element has been replaced');
     $this->assertEquals(1, count($markupXml->xpath(".//*[name(.)='img']")));
     $this->assertEquals(1, count($markupXml->xpath(".//*[name(.)='m:math']")));
 }
 /**
  * @param core_kernel_classes_Resource $item
  * @param string $lang
  * @param Directory $publicDirectory
  * @return qti\Item
  * @throws taoItems_models_classes_CompilationFailedException
  */
 protected function retrieveAssets(core_kernel_classes_Resource $item, $lang, Directory $publicDirectory)
 {
     $qtiItem = Service::singleton()->getDataItemByRdfItem($item, $lang);
     $assetParser = new AssetParser($qtiItem, $publicDirectory);
     $assetParser->setGetSharedLibraries(false);
     $assetParser->setGetXinclude(false);
     $resolver = new ItemMediaResolver($item, $lang);
     $replacementList = array();
     foreach ($assetParser->extract() as $type => $assets) {
         foreach ($assets as $assetUrl) {
             foreach (self::$BLACKLIST as $blacklist) {
                 if (preg_match($blacklist, $assetUrl) === 1) {
                     continue 2;
                 }
             }
             $mediaAsset = $resolver->resolve($assetUrl);
             $mediaSource = $mediaAsset->getMediaSource();
             $basename = $mediaSource->getBaseName($mediaAsset->getMediaIdentifier());
             $replacement = $basename;
             $count = 0;
             while (in_array($replacement, $replacementList)) {
                 $dot = strrpos($basename, '.');
                 $replacement = $dot !== false ? substr($basename, 0, $dot) . '_' . $count . substr($basename, $dot) : $basename . $count;
                 $count++;
             }
             $replacementList[$assetUrl] = $replacement;
             $tmpfile = $mediaSource->download($mediaAsset->getMediaIdentifier());
             $fh = fopen($tmpfile, 'r');
             $publicDirectory->writeStream($lang . '/' . $replacement, $fh);
             fclose($fh);
             unlink($tmpfile);
             //$fileStream = $mediaSource->getFileStream($mediaAsset->getMediaIdentifier());
             //$publicDirectory->writeStream($lang.'/'.$replacement, $fileStream);
         }
     }
     $dom = new \DOMDocument('1.0', 'UTF-8');
     if ($dom->loadXML($qtiItem->toXml()) === true) {
         $xpath = new \DOMXPath($dom);
         $attributeNodes = $xpath->query('//@*');
         foreach ($attributeNodes as $node) {
             if (isset($replacementList[$node->value])) {
                 $node->value = $replacementList[$node->value];
             }
         }
         $attributeNodes = $xpath->query("//*[local-name()='entry']") ?: [];
         unset($xpath);
         foreach ($attributeNodes as $node) {
             $node->nodeValue = strtr(htmlentities($node->nodeValue, ENT_XML1), $replacementList);
         }
     } else {
         throw new taoItems_models_classes_CompilationFailedException('Unable to load XML');
     }
     $qtiParser = new Parser($dom->saveXML());
     $assetRetrievedQtiItem = $qtiParser->load();
     //loadxinclude
     $xincludeLoader = new XIncludeLoader($assetRetrievedQtiItem, $resolver);
     $xincludeLoader->load(true);
     return $assetRetrievedQtiItem;
 }
 /**
  * 
  * @param core_kernel_classes_Resource $item
  * @param string $lang
  * @param string $destination
  * @return \oat\taoQtiItem\model\qti\Item
  */
 protected function retrieveAssets(core_kernel_classes_Resource $item, $lang, $destination)
 {
     $xml = taoItems_models_classes_ItemsService::singleton()->getItemContent($item);
     $qtiParser = new Parser($xml);
     $qtiItem = $qtiParser->load();
     $assetParser = new AssetParser($qtiItem);
     $assetParser->setGetSharedLibraries(false);
     $assetParser->setGetXinclude(false);
     $resolver = new ItemMediaResolver($item, $lang);
     foreach ($assetParser->extract() as $type => $assets) {
         foreach ($assets as $assetUrl) {
             foreach (self::$BLACKLIST as $blacklist) {
                 if (preg_match($blacklist, $assetUrl) === 1) {
                     continue 2;
                 }
             }
             $mediaAsset = $resolver->resolve($assetUrl);
             $mediaSource = $mediaAsset->getMediaSource();
             $srcPath = $mediaSource->download($mediaAsset->getMediaIdentifier());
             $filename = \tao_helpers_File::getSafeFileName(ltrim($mediaAsset->getMediaIdentifier(), '/'), $destination);
             $replacement = $mediaAsset->getMediaIdentifier();
             if (get_class($mediaSource) !== 'oat\\tao\\model\\media\\sourceStrategy\\HttpSource') {
                 $fileInfo = $mediaSource->getFileInfo($mediaAsset->getMediaIdentifier());
                 $filename = $fileInfo['filePath'];
                 if ($mediaAsset->getMediaIdentifier() !== $fileInfo['uri']) {
                     $replacement = $filename;
                 }
             }
             $destPath = ltrim($filename, '/');
             tao_helpers_File::copy($srcPath, $destination . $destPath, false);
             $xml = str_replace($assetUrl, $replacement, $xml);
         }
     }
     $qtiParser = new Parser($xml);
     $assetRetrievedQtiItem = $qtiParser->load();
     //loadxinclude
     $xincludeLoader = new XIncludeLoader($assetRetrievedQtiItem, $resolver);
     $xincludeLoader->load(true);
     return $assetRetrievedQtiItem;
 }
 /**
  * @param core_kernel_classes_Resource $item the item to pack
  * @param string $lang
  * @param Item $qtiItem
  * @param \oat\oatbox\filesystem\Directory $directory
  * @return ItemPack $itemPack
  * @throws common_Exception
  */
 public function packQtiItem($item, $lang, $qtiItem, Directory $directory)
 {
     //use the QtiParser to transform the QTI XML into an assoc array representation
     try {
         //build the ItemPack from the parsed data
         if ($this->replaceXinclude) {
             $resolver = new ItemMediaResolver($item, $lang);
             $xincludeLoader = new XIncludeLoader($qtiItem, $resolver);
             $xincludeLoader->load(true);
         }
         $itemPack = new ItemPack(self::$itemType, $qtiItem->toArray());
         $itemPack->setAssetEncoders($this->getAssetEncoders());
         $assetParser = new AssetParser($qtiItem, $directory);
         $assetParser->setDeepParsing($this->isNestedResourcesInclusion());
         $assetParser->setGetXinclude(!$this->replaceXinclude);
         $storageDirectory = new \tao_models_classes_service_StorageDirectory($item->getUri(), $directory->getFileSystemId(), $directory->getPrefix() . '/' . $lang);
         $storageDirectory->setServiceLocator($directory->getServiceLocator());
         foreach ($assetParser->extract($itemPack) as $type => $assets) {
             $resolver = new ItemMediaResolver($item, $lang);
             foreach ($assets as &$asset) {
                 $mediaAsset = $resolver->resolve($asset);
                 $mediaSource = $mediaAsset->getMediaSource();
                 $asset = $mediaSource->getBaseName($mediaAsset->getMediaIdentifier());
             }
             $itemPack->setAssets($type, $assets, $storageDirectory);
         }
     } catch (common_Exception $e) {
         throw new common_Exception('Unable to pack item ' . $item->getUri() . ' : ' . $e->getMessage());
     }
     return $itemPack;
 }