2010-03-18 6 views
5

Sto utilizzando lo DOM extension per analizzare un file xml contenente xml namespaces. Avrei pensato che le dichiarazioni dei namespace sono trattate come qualsiasi altro attributo, ma i miei test sembrano non essere d'accordo. Ho un documento che inizia così:PHP: richiama tutti gli spazi dei nomi dichiarati di una DOMElement

<rdf:RDF 
    xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#" 
    xmlns="http://purl.org/rss/1.0/" 
    xmlns:taxo="http://purl.org/rss/1.0/modules/taxonomy/" 
    xmlns:dc="http://purl.org/dc/elements/1.1/" 
    xmlns:syn="http://purl.org/rss/1.0/modules/syndication/" 
    xmlns:prism="http://purl.org/rss/1.0/modules/prism/" 
    xmlns:admin="http://webns.net/mvcb/" 
    > 

E un codice di test come questo:

$doc = new DOMDocument(); 
$doc->loadXml(file_get_contents('/home/soulmerge/tmp/rss1.0/recent.xml')); 
$root = $doc->documentElement; 
var_dump($root->tagName); 
# prints 'string(7) "rdf:RDF"' 
var_dump($root->attributes->item(0)); 
# prints 'NULL' 
var_dump($root->getAttributeNode('xmlns')); 
# prints 'object(DOMNameSpaceNode)#3 (0) {}' 

Quindi le domande sono:

  1. Qualcuno sa dove potrei trovare la documentazione di DOMNameSpaceNode? A search on php.net non produce alcun risultato utile.
  2. Come estrarre tutte quelle dichiarazioni dello spazio dei nomi da quel DOMElement?

risposta

9

A meno che non vi sia un modo più diretto, è possibile utilizzare XPath e il suo namespace axis.
ad es.

<?php 
$doc = new DOMDocument; 
$doc->loadxml('<rdf:RDF 
    xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#" 
    xmlns="http://purl.org/rss/1.0/" 
    xmlns:taxo="http://purl.org/rss/1.0/modules/taxonomy/" 
    xmlns:dc="http://purl.org/dc/elements/1.1/" 
    xmlns:syn="http://purl.org/rss/1.0/modules/syndication/" 
    xmlns:prism="http://purl.org/rss/1.0/modules/prism/" 
    xmlns:admin="http://webns.net/mvcb/" 
    > 
... 
</rdf:RDF>'); 
$context = $doc->documentElement; 

$xpath = new DOMXPath($doc); 
foreach($xpath->query('namespace::*', $context) as $node) { 
    echo $node->nodeValue, "\n"; 
} 

stampe

http://www.w3.org/XML/1998/namespace 
http://webns.net/mvcb/ 
http://purl.org/rss/1.0/modules/prism/ 
http://purl.org/rss/1.0/modules/syndication/ 
http://purl.org/dc/elements/1.1/ 
http://purl.org/rss/1.0/modules/taxonomy/ 
http://purl.org/rss/1.0/ 
http://www.w3.org/1999/02/22-rdf-syntax-ns# 

modificare e btw: non ho trovato la documentazione per DOMNameSpaceNode sia. Ma si può "dedurre" (parti di) la sua funzionalità dal codice sorgente in ext/dom/php_dom.c
non sembra esporre tutti i metodi ed espone le proprietà

"nodeName", "nodeValue", "nodeType", 
"prefix", "localName", "namespaceURI", 
"ownerDocument", "parentNode" 

tutti gestiti dalla stesse funzioni delle proprietà del DOMNode corrispondenti.

+0

Mille grazie, questa è sicuramente una soluzione funzionante. Suppongo che dovrò aspettare fino a quando la documentazione php non verrà aggiornata per ottenere l'implementazione giusta. – soulmerge

2

nota, che

echo $root->getAttributeNode('xmlns')->nodeValue . "\n"; 
echo $root->getAttribute('xmlns') . "\n"; 
echo $root->getAttribute('xmlns:syn') . "\n"; 

tutto il lavoro come previsto, e stampare

http://purl.org/rss/1.0/ 
http://purl.org/rss/1.0/ 
http://purl.org/rss/1.0/modules/syndication/ 

perché DOMNameSpaceNode è un nodo, non un NodeCollection.

Basta chiarire che, a meno che qualcosa nell'estensione del DOM PHP non cambi, XPath (come spiegato da VolkerK) è l'unico modo nativo per ottenere tutti gli spazi dei nomi, indipendentemente dalla documentazione.

Problemi correlati