77use DOMElement ;
88use SimpleSAML \XMLSecurity \Constants as C ;
99use SimpleSAML \XMLSecurity \Exception \CanonicalizationFailedException ;
10+ use SimpleSAML \XMLSecurity \Exception \ReferenceValidationFailedException ;
11+ use SimpleSAML \XMLSecurity \Utils \XPath ;
1012use SimpleSAML \XMLSecurity \XML \ds \Transforms ;
1113use SimpleSAML \XPath \Constants as XPATH_C ;
1214
@@ -34,7 +36,7 @@ abstract protected function getOriginalXML(): DOMElement;
3436 * @param \DOMElement $element The DOM element that needs canonicalization.
3537 * @param string $c14nMethod The identifier of the canonicalization algorithm to use.
3638 * See \SimpleSAML\XMLSecurity\Constants.
37- * @param string[] |null $xpaths An array of xpaths to filter the nodes by. Defaults to null (no filters).
39+ * @param array<mixed> |null $xpaths An array of xpaths to filter the nodes by. Defaults to null (no filters).
3840 * @param string[]|null $prefixes An array of namespace prefixes to filter the nodes by.
3941 * Defaults to null (no filters).
4042 *
@@ -121,6 +123,7 @@ public function processTransforms(
121123 $ canonicalMethod = C::C14N_EXCLUSIVE_WITHOUT_COMMENTS ;
122124 $ arXPath = null ;
123125 $ prefixList = null ;
126+
124127 foreach ($ transforms ->getTransform () as $ transform ) {
125128 $ canonicalMethod = $ transform ->getAlgorithm ()->getValue ();
126129 switch ($ canonicalMethod ) {
@@ -141,14 +144,20 @@ public function processTransforms(
141144 $ xpathValue = $ xpath ->getContent ()->getValue ();
142145 $ arXPath ['query ' ] = '(.//. | .//@* | .//namespace::*)[ ' . $ xpathValue . '] ' ;
143146
144- // $arXpath['namespaces'] = $xpath->getNamespaces();
145- // TODO: review if $nsnode->localName is equivalent to the keys in getNamespaces()
146- // $nslist = $xp->query('./namespace::*', $node);
147- // foreach ($nslist as $nsnode) {
148- // if ($nsnode->localName != "xml") {
149- // $arXPath['namespaces'][$nsnode->localName] = $nsnode->nodeValue;
150- // }
151- // }
147+ $ xpCache = XPath::getXPath ($ transform ->toXML ());
148+ $ nslist = $ xpCache ->query ('./namespace::* ' , $ data );
149+ Assert::lessThanEq (
150+ $ nslist ->count (),
151+ C::MAX_XPATH_NAMESPACES ,
152+ ReferenceValidationFailedException::class,
153+ 'Too many namespaces. ' ,
154+ );
155+
156+ foreach ($ nslist as $ nsnode ) {
157+ if ($ nsnode ->localName != "xml " ) {
158+ $ arXPath ['namespaces ' ][$ nsnode ->localName ] = $ nsnode ->nodeValue ;
159+ }
160+ }
152161 }
153162 break ;
154163 }
0 commit comments