2011-05-25 36 views
17

Tengo un documento XML y una expresión XPath para ese documento. Tengo que actualizar el documento usando XPath en tiempo de ejecución.Cómo actualizar XML utilizando XPath y Java

¿Cómo puedo hacer esto usando Java?

A continuación es mi xml:

<?xml version="1.0" encoding="ISO-8859-1"?> 
<PersonList> 
    <Person> 
     <Name>Sonu Kapoor</Name> 
     <Age>24</Age> 
     <Gender>M</Gender> 
     <PostalCode>54879</PostalCode> 
    </Person> 
    <Person> 
     <Name>Jasmin</Name> 
     <Age>28</Age> 
     <Gender>F</Gender> 
     <PostalCode>78745</PostalCode> 
    </Person> 
    <Person> 
     <Name>Josef</Name> 
     <Age>232</Age> 
     <Gender>F</Gender> 
     <PostalCode>53454</PostalCode> 
    </Person> 
</PersonList> 

tengo que cambiar los valores de nombre y edad menor //PersonList/Person[2]/Name.

Respuesta

23

Uso setNodeValue. En primer lugar, obtener un NodeList, por ejemplo:

myNodeList = (NodeList) xpath.compile("//MyXPath/text()") 
      .evaluate(myXmlDoc, XPathConstants.NODESET); 

Entonces establece el valor de, por ejemplo, el primer nodo:

myNodeList.item(0).setNodeValue("Hi mom!"); 

Más ejemplos, p. here.

Como se menciona en otras dos respuestas aquí, así como en su previous question: técnicamente, XPath no es una forma de "actualizar" un documento XML, sino solo de localizar nodos dentro de un documento XML. Pero supongo que lo anterior es lo que quieres.

EDITAR: En respuesta a su comentario ... ¿Está usted preguntando cómo escribir el DOM en un archivo XML después de que haya terminado de editar el DOM? Si es así, aquí hay dos ejemplos de cómo hacerlo:

http://www.java2s.com/Code/Java/XML/WriteDOMout.htm

http://download.oracle.com/javaee/1.4/tutorial/doc/JAXPXSLT4.html

+0

en este paso ya lo he hecho. Pero ahora cómo configurar este objeto nodo en document.we no puede usar doc.appendChild (myNodeList.item (0)) ;. porque no queremos agregar el nuevo nodo que quiero simplemente establecer el valor de un elemento. Para esto, ¿necesitamos eliminar el nodo anterior y agregar otro nodo con valores actualizados ... ???? – samash

+0

Gracias. ¿Qué pasa si necesito cambiar el atributo de nodo? – Dejell

3

XPath se utiliza para seleccionar partes de un documento XML. No tiene ninguna disposición para la actualización. Pero dado que devuelve objetos DOM (Elementos, si la memoria se sirve, o tal vez Nodos), entonces puede usar métodos DOM para alterar el documento.

3

XPath se puede utilizar para seleccionar nodos en un documento, no para la modificación

aplicar la expresión XPath a su documento y obtener un elemento (en su caso). Una vez que tenga esta Element, puede utilizar los métodos Element para cambiar los valores (nombre y edad en su caso)


A partir de un NodeList que debería funcionar así:

NodeList nodes = getNodeListFromXPathExpression(); // you know how 
if (nodes.length == 0) 
    return; // empty nodelist, xpath didn't select anything 

Node first = node.getItem(0); // take the first from the list, your element 

// this is a shortcut for your example: 
// first is the actual selected element (a node) 
// .getFirst() returns the first child node, the "text node" (="Jasmine", ="28") 
// .setNodeValue() replace the actual value of that text node with a new string 
first.getFirstChild().setNodeValue("New Name or new age"); 
+0

puedo conseguir lista de nodos de expresión XPath pero después de eso cómo modificar con eso ... Can u por favor ponga una pieza de muestra de código .... no soy experto en XML ....... – samash

1

considerar el uso de XQuery Update en lugar de XPath. Esto le permite escribir

replace value of node //PersonList/Person[2]/Name with "Anonymous" 

Esto es mucho más fácil que usar la API DOM de Java.

+0

Pero no estoy al tanto de xquey y cómo incrustar esta consulta en java ... – samash

+0

¿Podría proporcionar un enlace a un SSSCE para esto? –

+0

@samesh, entonces es hora de que lo descubras. –

1

He creado un pequeño proyecto para el uso de XPath para crear/actualizar XML: https://github.com/shenghai/xmodifier el código para cambiar el código XML es como:

Document document = readDocument("personList.xml"); 
XModifier modifier = new XModifier(document); 
modifier.addModify("//PersonList/Person[2]/Name", "newName"); 
modifier.modify(); 
2

Puede borrar el archivo y crear una nueva.

Document doc = DocumentBuilderFactory.newInstance().newDocumentBuilder().parse(
    new InputSource("data.xml")); 

XPath xpath = XPathFactory.newInstance().newXPath(); 
NodeList nodes = (NodeList) xpath.evaluate("//employee/name[text()='old']", doc, 
    XPathConstants.NODESET); 

for (int idx = 0; idx < nodes.getLength(); idx++) { 
    nodes.item(idx).setTextContent("new value"); 
} 

Transformer xformer = TransformerFactory.newInstance().newTransformer(); 
xformer.transform(new DOMSource(doc), new StreamResult(new File("data_new.xml"))); 
0

Este es el código para cambiar el contenido con vtd-xml ... vtd-xml es único, ya que es la única API que ofrece una capacidad de actualización incremental.

import com.ximpleware.*; 
import java.io.*; 

public class changeName { 
    public static void main(String s[]) throws VTDException,java.io.UnsupportedEncodingException,java.io.IOException{ 
     VTDGen vg = new VTDGen(); 
     if (!vg.parseFile("input.xml", false)) 
      return; 
     VTDNav vn = vg.getNav(); 
     AutoPilot ap = new AutoPilot(vn); 
     XMLModifier xm = new XMLModifier(vn); 
     ap.selectXPath("//PersonList/Person[2]"); 
     int i=0; 
     while((i=ap.evalXPath())!=-1){ 
      if (vn.toElement(VTDNav.FIRST_CHILD,"Name")){ 
       int k=vn.getText(); 
       if (i!=-1) 
        xm.updateToken(k, "Jonathan"); 
       vn.toElement(VTDNav.PARENT); 
      } 
      if (vn.toElement(VTDNav.FIRST_CHILD,"Age")){ 
       int k=vn.getText(); 
       if (i!=-1) 
        xm.updateToken(k, "42"); 
       vn.toElement(VTDNav.PARENT); 
      } 
     } 
     xm.output("new.xml"); 
    } 
} 
Cuestiones relacionadas