From: John S. <jsi...@al...> - 2010-12-06 14:35:20
|
I am evaluating vtd-xml as a possible replacement for standard Java DOM and XPath implementations. We have an XMLUtility which has methods to insert structure into XML. I have done enough work to see that we can get significant performance improvements with vtd-xml, but right off the bat I hit this issue: The following test illustrates that if the starting XML is <foo></foo> that the method: private static String insert( String document, String xPath, String node ) throws Exception can be used to insert 'structure' into the XML. This is shown by: System.out.println(insert("<foo></foo>", "//foo", "bar")); This does not insert 'structure': System.out.println(insert("<foo></foo>", "//bogus", "bar")); That is correct behavior because the XPath //bogus is not found in the starting XML (<foo></foo>). The problem occurs with: System.out.println(insert("<foo/>", "//foo", "bar")); import java.io.ByteArrayOutputStream; import com.ximpleware.AutoPilot; import com.ximpleware.ModifyException; import com.ximpleware.VTDGen; import com.ximpleware.VTDNav; import com.ximpleware.XMLModifier; public class Insert { public static void main( String[] arguments ) throws Exception { System.out.println(insert("<foo></foo>", "//foo", "bar")); System.out.println(insert("<foo></foo>", "//bogus", "bar")); System.out.println(insert("<foo/>", "//foo", "bar")); } /** * Insert a node into an existing document. * @param document * @param xPath * @param node * @return * @throws Exception */ private static String insert( String document, String xPath, String node ) throws Exception { VTDGen vg = new VTDGen(); XMLModifier xm = new XMLModifier(); vg.setDoc(document.getBytes()); vg.parse(true); VTDNav vn = vg.getNav(); AutoPilot ap = new AutoPilot(vn); xm.bind(vn); ap.selectXPath(xPath); int xmlIndex = ap.evalXPath(); if ( xmlIndex > 0 ) { try { xm.insertAfterHead("</"+node+">"); } catch ( ModifyException me ) { System.out.println("Failed to insert: "+node+" at index: "+xmlIndex); throw me; } } ByteArrayOutputStream output = new ByteArrayOutputStream(); xm.output(output); return output.toString(); } } |