2009-02-12 15 views
13

Quiero usar JDOM para leer en un archivo XML, luego uso XPath para extraer datos del documento JDOM. Crea bien el objeto de documento, pero cuando uso XPath para consultar el documento para una lista de elementos, no obtengo nada.Espacio de nombres XML predeterminado, JDOM y XPath

Mi documento XML tiene un espacio de nombre predeterminado definido en el elemento raíz. Lo curioso es que cuando elimino el espacio de nombres predeterminado, ejecuta correctamente la consulta XPath y devuelve los elementos que quiero. ¿Qué más debo hacer para que mi consulta XPath devuelva resultados?

XML:

<?xml version="1.0" encoding="UTF-8"?> 
<collection xmlns="http://www.foo.com"> 
<dvd id="A"> 
    <title>Lord of the Rings: The Fellowship of the Ring</title> 
    <length>178</length> 
    <actor>Ian Holm</actor> 
    <actor>Elijah Wood</actor> 
    <actor>Ian McKellen</actor> 
</dvd> 
<dvd id="B"> 
    <title>The Matrix</title> 
    <length>136</length> 
    <actor>Keanu Reeves</actor> 
    <actor>Laurence Fishburne</actor> 
</dvd> 
</collection> 

Java:

public static void main(String args[]) throws Exception { 
    SAXBuilder builder = new SAXBuilder(); 
    Document d = builder.build("xpath.xml"); 
    XPath xpath = XPath.newInstance("collection/dvd"); 
    xpath.addNamespace(d.getRootElement().getNamespace()); 
    System.out.println(xpath.selectNodes(d)); 
} 

Respuesta

26

XPath 1.0 no es compatible con el concepto de un espacio de nombres por defecto (XPath 2.0 hace). Cualquier etiqueta no prefijada se asume siempre como parte del espacio de nombres sin nombre.

Al utilizar XPath 1.0 necesita algo como esto:

public static void main(String args[]) throws Exception { 
    SAXBuilder builder = new SAXBuilder(); 
    Document d = builder.build("xpath.xml"); 
    XPath xpath = XPath.newInstance("x:collection/x:dvd"); 
    xpath.addNamespace("x", d.getRootElement().getNamespaceURI()); 
    System.out.println(xpath.selectNodes(d)); 
} 
+0

¡Lo hice, gracias! – Michael

+0

Esto es excelente, pasé las últimas 3 horas preguntándome por qué mi XPath de repente no funcionaba y era esto. Pffh! :) – Esko

+0

¿Para qué es la x? – Meinkraft

6

que tenía un problema similar, pero la mía era que tenía una mezcla de entradas XML, algunos de los cuales tenían un espacio de nombres definido y demás eso no. Para simplificar mi problema, ejecuté el siguiente fragmento de JDOM después de cargar el documento.

for (Element el : doc.getRootElement().getDescendants(new ElementFilter())) { 
    if (el.getNamespace() != null) el.setNamespace(null); 
} 

Después de la eliminación de todos los espacios de nombres que fue capaz de utilizar sencilla GetChild ("elname") de navegación estilo o consultas XPath simples.

No recomendaría esta técnica como una solución general, pero en mi caso fue definitivamente útil.

+0

Gracias por la sugerencia. Pensé en hacer algo así, pero al igual que aludiste, eliminar los espacios de nombres significa que existe la posibilidad de que te encuentres con colisiones de nombres, dependiendo de cómo sean tus datos XML. – Michael

1

También puede hacer lo siguiente

/*[local-name() = 'collection']/*[local-name() = 'dvd']/

Here es la lista de las consultas XPath útiles.

Cuestiones relacionadas