315 lines
14 KiB
PHP
315 lines
14 KiB
PHP
<?php
|
|
|
|
/**
|
|
* This program is free software; you can redistribute it and/or
|
|
* modify it under the terms of the GNU General Public License
|
|
* as published by the Free Software Foundation; under version 2
|
|
* of the License (non-upgradable).
|
|
*
|
|
* This program is distributed in the hope that it will be useful,
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
* GNU General Public License for more details.
|
|
*
|
|
* You should have received a copy of the GNU General Public License
|
|
* along with this program; if not, write to the Free Software
|
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
|
*
|
|
* Copyright (c) 2014 (original work) Open Assessment Technologies SA;
|
|
*/
|
|
|
|
namespace oat\taoQtiItem\test\integration\metadata;
|
|
|
|
use oat\taoQtiItem\model\qti\metadata\simple\SimpleMetadataValue;
|
|
use oat\taoQtiItem\model\qti\metadata\imsManifest\ImsManifestMapping;
|
|
use oat\tao\test\TaoPhpUnitTestRunner;
|
|
use oat\taoQtiItem\model\qti\metadata\imsManifest\ImsManifestMetadataInjector;
|
|
use \DOMXPath;
|
|
use \DOMDocument;
|
|
|
|
include_once dirname(__FILE__) . '/../../../includes/raw_start.php';
|
|
|
|
class ImsManifestInjectionTest extends TaoPhpUnitTestRunner
|
|
{
|
|
protected $imsManifestInjector;
|
|
|
|
public function setUp(): void
|
|
{
|
|
parent::setUp();
|
|
$this->imsManifestInjector = new ImsManifestMetadataInjector();
|
|
}
|
|
|
|
public function tearDown(): void
|
|
{
|
|
parent::tearDown();
|
|
unset($this->imsManifestInjector);
|
|
}
|
|
|
|
/**
|
|
* @dataProvider injectionProvider
|
|
*
|
|
* @param string $inputFile
|
|
* @param array $values
|
|
* @param array $mappings
|
|
*/
|
|
public function testInjection($inputFile, array $values, array $mappings)
|
|
{
|
|
$imsManifest = new DOMDocument('1.0', 'UTF-8');
|
|
$imsManifest->load(dirname(__FILE__) . "/../samples/metadata/imsManifestInjection/${inputFile}");
|
|
|
|
|
|
// Register mappings...
|
|
foreach ($mappings as $mapping) {
|
|
$this->imsManifestInjector->addMapping($mapping);
|
|
}
|
|
|
|
$this->imsManifestInjector->inject($imsManifest, $values);
|
|
$newDom = new DOMDocument('1.0', 'UTF-8');
|
|
$newDom->loadXML($imsManifest->saveXML());
|
|
$imsManifest = $newDom;
|
|
|
|
$xpath = new DOMXpath($imsManifest);
|
|
$xpath->registerNamespace('man', $imsManifest->documentElement->namespaceURI);
|
|
|
|
// Check everything is fine regarding mappings...
|
|
foreach ($mappings as $mapping) {
|
|
$prefix = $mapping->getPrefix();
|
|
$ns = $mapping->getNamespace();
|
|
$sc = $mapping->getSchemaLocation();
|
|
|
|
$xpath->registerNamespace($prefix, $ns);
|
|
$manifestElt = $imsManifest->documentElement;
|
|
$this->assertEquals('manifest', $manifestElt->tagName, "No <manifest> element found as the root XML element for file '${inputFile}'.");
|
|
|
|
// Check that the namespace is correctly declared in <manifest> element.
|
|
$this->assertTrue($manifestElt->hasAttributeNS('http://www.w3.org/2000/xmlns/', "${prefix}"), "No namespace with prefix '${prefix}' declared in <manifest> element for file '${inputFile}'.");
|
|
$nsDeclaration = $manifestElt->getAttribute("xmlns:${prefix}");
|
|
$this->assertEquals($ns, $nsDeclaration, "Namespace declaration for namespace '${ns}' with prefix '${prefix}' in <manifest> element does not match for file '${inputFile}'.");
|
|
|
|
// Check that we get the tuple in xsi:schemaLocation.
|
|
$this->assertTrue($manifestElt->hasAttribute('xsi:schemaLocation'), "No xsd:schemaLocation attribute found in <manifest> element for file '${inputFile}'.");
|
|
$schemaLocations = $manifestElt->getAttribute('xsi:schemaLocation');
|
|
|
|
$xsiPattern = '@' . preg_quote($ns) . "\\s+" . preg_quote($sc) . '@';
|
|
$this->assertEquals(1, preg_match($xsiPattern, $schemaLocations), "No xsi:schemaLocation found for namespace '${ns}' in file '${inputFile}'.");
|
|
}
|
|
|
|
foreach ($values as $resourceIdentifier => $metadataValues) {
|
|
foreach ($metadataValues as $metadataValue) {
|
|
$path = $metadataValue->getPath();
|
|
$query = "//man:resource[@identifier='${resourceIdentifier}']/man:metadata";
|
|
|
|
foreach ($path as $pathComponent) {
|
|
$parts = explode('#', $pathComponent);
|
|
$base = $parts[0];
|
|
$tag = $parts[1];
|
|
|
|
// do we have a namespace mapping for that?
|
|
$mappings = $this->imsManifestInjector->getMappings();
|
|
$mapping = null;
|
|
foreach ($mappings as $m) {
|
|
if ($m->getNamespace() === $base) {
|
|
$mapping = $m;
|
|
break;
|
|
}
|
|
}
|
|
|
|
$prefix = $mapping->getPrefix();
|
|
$query .= "/${prefix}:${tag}";
|
|
}
|
|
|
|
// Do we have something at location?
|
|
$elts = $xpath->query($query);
|
|
$this->assertGreaterThanOrEqual(1, $elts->length, "Nothing found in XML at path '" . implode(' -> ', $path) . "' in file '${inputFile}'.");
|
|
$hasLang = $metadataValue->getLanguage() !== '';
|
|
|
|
// Does one of the values contain the expected value?
|
|
for ($i = 0; $i < $elts->length; $i++) {
|
|
$valueMatch = $elts->item($i)->nodeValue === $metadataValue->getValue();
|
|
$langMatch = false;
|
|
|
|
if ($hasLang === false || $elts->item($i)->getAttribute('xml:lang') === $metadataValue->getLanguage()) {
|
|
$langMatch = true;
|
|
}
|
|
|
|
if ($valueMatch === true && $langMatch === true) {
|
|
break;
|
|
}
|
|
}
|
|
|
|
$this->assertLessThan($elts->length, $i, "No matching value found at path '" . implode(' -> ', $path) . "' in file '${inputFile}'.");
|
|
}
|
|
}
|
|
}
|
|
|
|
public function injectionProvider()
|
|
{
|
|
return [
|
|
[
|
|
'sample1.xml',
|
|
[
|
|
'choice' => [
|
|
new SimpleMetadataValue(
|
|
'choice',
|
|
[
|
|
'http://www.imsglobal.org/xsd/imsmd_v1p2#lom',
|
|
'http://www.imsglobal.org/xsd/imsmd_v1p2#general',
|
|
'http://www.imsglobal.org/xsd/imsmd_v1p2#identifier'
|
|
],
|
|
'qti_v2_item_01'
|
|
)
|
|
]
|
|
],
|
|
[
|
|
new ImsManifestMapping('http://www.imsglobal.org/xsd/imsmd_v1p2', 'imsmd', 'http://www.imsglobal.org/xsd/imsmd_v1p2p2.xsd')
|
|
]
|
|
],
|
|
|
|
[
|
|
'sample2.xml',
|
|
[
|
|
'choice' => [
|
|
new SimpleMetadataValue(
|
|
'choice',
|
|
[
|
|
'http://www.imsglobal.org/xsd/imsmd_v1p2#lom',
|
|
'http://www.imsglobal.org/xsd/imsmd_v1p2#general',
|
|
'http://www.imsglobal.org/xsd/imsmd_v1p2#identifier'
|
|
],
|
|
'qti_v2_item_01'
|
|
),
|
|
new SimpleMetadataValue(
|
|
'choice',
|
|
[
|
|
'http://www.imsglobal.org/xsd/imsmd_v1p2#lom',
|
|
'http://www.imsglobal.org/xsd/imsmd_v1p2#general',
|
|
'http://www.imsglobal.org/xsd/imsmd_v1p2#title',
|
|
'http://www.imsglobal.org/xsd/imsmd_v1p2#langstring'
|
|
],
|
|
'Metadata Example Item #1',
|
|
'en'
|
|
),
|
|
new SimpleMetadataValue(
|
|
'choice',
|
|
[
|
|
'http://www.imsglobal.org/xsd/imsmd_v1p2#lom',
|
|
'http://www.imsglobal.org/xsd/imsmd_v1p2#general',
|
|
'http://www.imsglobal.org/xsd/imsmd_v1p2#description',
|
|
'http://www.imsglobal.org/xsd/imsmd_v1p2#langstring'
|
|
],
|
|
'This is a dummy item',
|
|
'en'
|
|
),
|
|
new SimpleMetadataValue(
|
|
'choice',
|
|
[
|
|
'http://www.imsglobal.org/xsd/imsqti_v2p0#qtiMetadata',
|
|
'http://www.imsglobal.org/xsd/imsqti_v2p0#timeDependent'
|
|
],
|
|
'false'
|
|
),
|
|
new SimpleMetadataValue(
|
|
'choice',
|
|
[
|
|
'http://www.imsglobal.org/xsd/imsqti_v2p0#qtiMetadata',
|
|
'http://www.imsglobal.org/xsd/imsqti_v2p0#interactionType'
|
|
],
|
|
'choiceInteraction'
|
|
),
|
|
new SimpleMetadataValue(
|
|
'choice',
|
|
[
|
|
'http://www.imsglobal.org/xsd/imsqti_v2p0#qtiMetadata',
|
|
'http://www.imsglobal.org/xsd/imsqti_v2p0#feedbackType'
|
|
],
|
|
'nonadaptive'
|
|
),
|
|
new SimpleMetadataValue(
|
|
'choice',
|
|
[
|
|
'http://www.imsglobal.org/xsd/imsqti_v2p0#qtiMetadata',
|
|
'http://www.imsglobal.org/xsd/imsqti_v2p0#solutionAvailable'
|
|
],
|
|
'true'
|
|
),
|
|
new SimpleMetadataValue(
|
|
'choice',
|
|
[
|
|
'http://www.imsglobal.org/xsd/imsqti_v2p0#qtiMetadata',
|
|
'http://www.imsglobal.org/xsd/imsqti_v2p0#toolName'
|
|
],
|
|
'XMLSPY'
|
|
),
|
|
new SimpleMetadataValue(
|
|
'choice',
|
|
[
|
|
'http://www.imsglobal.org/xsd/imsqti_v2p0#qtiMetadata',
|
|
'http://www.imsglobal.org/xsd/imsqti_v2p0#toolVersion'
|
|
],
|
|
'5.4'
|
|
),
|
|
new SimpleMetadataValue(
|
|
'choice',
|
|
[
|
|
'http://www.imsglobal.org/xsd/imsqti_v2p0#qtiMetadata',
|
|
'http://www.imsglobal.org/xsd/imsqti_v2p0#toolVendor'
|
|
],
|
|
'ALTOVA'
|
|
)
|
|
],
|
|
'hybrid' => [
|
|
new SimpleMetadataValue(
|
|
'hybrid',
|
|
[
|
|
'http://www.imsglobal.org/xsd/imsmd_v1p2#lom',
|
|
'http://www.imsglobal.org/xsd/imsmd_v1p2#general',
|
|
'http://www.imsglobal.org/xsd/imsmd_v1p2#identifier'
|
|
],
|
|
'qti_v2_item_02'
|
|
),
|
|
new SimpleMetadataValue(
|
|
'hybrid',
|
|
[
|
|
'http://www.imsglobal.org/xsd/imsqti_v2p0#qtiMetadata',
|
|
'http://www.imsglobal.org/xsd/imsqti_v2p0#interactionType'
|
|
],
|
|
'choiceInteraction'
|
|
),
|
|
new SimpleMetadataValue(
|
|
'hybrid',
|
|
[
|
|
'http://www.imsglobal.org/xsd/imsqti_v2p0#qtiMetadata',
|
|
'http://www.imsglobal.org/xsd/imsqti_v2p0#interactionType'
|
|
],
|
|
'orderInteraction'
|
|
),
|
|
],
|
|
],
|
|
[
|
|
new ImsManifestMapping('http://www.imsglobal.org/xsd/imsmd_v1p2', 'imsmd', 'http://www.imsglobal.org/xsd/imsmd_v1p2p2.xsd'),
|
|
new ImsManifestMapping('http://www.imsglobal.org/xsd/imsqti_v2p0', 'imsqti', 'http://www.imsglobal.org/xsd/imsqti_v2p0.xsd')
|
|
]
|
|
],
|
|
|
|
[
|
|
'sample3.xml',
|
|
[
|
|
'Q01' => [
|
|
new SimpleMetadataValue(
|
|
'choice',
|
|
[
|
|
'http://www.taotesting.com/xsd/mpm#myprojectMetadata',
|
|
'http://www.taotesting.com/xsd/mpm#complexity'
|
|
],
|
|
'4'
|
|
)
|
|
]
|
|
],
|
|
[
|
|
new ImsManifestMapping('http://www.taotesting.com/xsd/mpm', 'mpm', 'http://www.taotesting.com/xsd/mpm.xsd')
|
|
]
|
|
],
|
|
];
|
|
}
|
|
}
|