I am writing a java function that is parsing an xml element & extracting the given xpath expression. Below is the function :
public static Node getDataNode(Element payload, final HashMap<String, String> namespaces, String xpathStr) {
Node node = null;
try {
// Create a namespace context based on the namespaces passed in.
NamespaceContext ctx = new NamespaceContext() {
public String getNamespaceURI(String prefix) {
return namespaces.get(prefix);
}
public Iterator getPrefixes(String val) {
return null;
}
public String getPrefix(String uri) {
return null;
}
};
XPathFactory xpathFact = XPathFactory.newInstance();
XPath xpath = xpathFact.newXPath();
xpath.setNamespaceContext(ctx);
XPathExpression expr = xpath.compile(xpathStr);
System.out.println("Got request to process node : " + payload.getLocalName() + " with " + xpathStr);
System.out.println(xpathStr + " has been compiled successfully.");
((XMLElement) payload).print(System.out);
node = (Node) expr.evaluate(payload, XPathConstants.NODE);
} catch (XPathExpressionException ex) {
ex.printStackTrace();
return null;
} catch (IOException io) {
io.printStackTrace();
return null;
}
return node;
}
Below is the logs for this part of function :
Got request to process node : Body with ".//soapenv:Body/pip:request"
".//soapenv:Body/pip:request" has been compiled successfully.
<soapenv:Body xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">
<pip:request xmlns:pip="http://xmlns.oracle.com/ServiceBusApplication/UserInterfaceTest/Pipeline">textContent</pip:request>
</soapenv:Body>
I have tried different xpath expression like //soapenv:Body/pip:request, .//soapenv:Body/pip:request but still i am getting the error :
com.sun.org.apache.xpath.internal.XPathException: Can not convert #STRING to a NodeList! at com.sun.org.apache.xpath.internal.objects.XObject.error(XObject.java:711) at com.sun.org.apache.xpath.internal.objects.XObject.nodeset(XObject.java:441) at com.sun.org.apache.xpath.internal.jaxp.XPathExpressionImpl.getResultAsType(XPathExpressionImpl.java:357) at com.sun.org.apache.xpath.internal.jaxp.XPathExpressionImpl.eval(XPathExpressionImpl.java:101) at com.sun.org.apache.xpath.internal.jaxp.XPathExpressionImpl.evaluate(XPathExpressionImpl.java:182)
Please let me know what is wrong in the code.Appreciate your help in resolving the issue . Thanks.
Unable to reproduce. Tested with MCVE code below on Oracle JDK 1.5 and on Oracle JDK 9.
Only change made to getDataNode
method is commenting out the ((XMLElement) payload).print(System.out)
statement, since Oracle JDK doesn't have an XMLElement
type.
Test
import java.io.StringReader;
import java.util.HashMap;
import java.util.Iterator;
import javax.xml.namespace.NamespaceContext;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.xpath.XPath;
import javax.xml.xpath.XPathConstants;
import javax.xml.xpath.XPathExpression;
import javax.xml.xpath.XPathExpressionException;
import javax.xml.xpath.XPathFactory;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.Node;
import org.xml.sax.InputSource;
String xml = "<soapenv:Body xmlns:soapenv=\"http://schemas.xmlsoap.org/soap/envelope/\">\n" +
" <pip:request xmlns:pip=\"http://xmlns.oracle.com/ServiceBusApplication/UserInterfaceTest/Pipeline\">textContent</pip:request>\n" +
" </soapenv:Body>";
DocumentBuilderFactory domFactory = DocumentBuilderFactory.newInstance();
domFactory.setNamespaceAware(true);
DocumentBuilder domBuilder = domFactory.newDocumentBuilder();
Document document = domBuilder.parse(new InputSource(new StringReader(xml)));
HashMap<String, String> namespaces = new HashMap<String, String>();
namespaces.put("soapenv", "http://schemas.xmlsoap.org/soap/envelope/");
namespaces.put("pip", "http://xmlns.oracle.com/ServiceBusApplication/UserInterfaceTest/Pipeline");
Node node = getDataNode(document.getDocumentElement(), namespaces, ".//soapenv:Body/pip:request");
System.out.println(node != null ? node.getTextContent() : null);
node = getDataNode(document.getDocumentElement(), namespaces, "/soapenv:Body/pip:request");
System.out.println(node != null ? node.getTextContent() : null);
node = getDataNode(document.getDocumentElement(), namespaces, ".//pip:request");
System.out.println(node != null ? node.getTextContent() : null);
Output
Got request to process node : Body with .//soapenv:Body/pip:request
.//soapenv:Body/pip:request has been compiled successfully.
null
Got request to process node : Body with /soapenv:Body/pip:request
/soapenv:Body/pip:request has been compiled successfully.
textContent
Got request to process node : Body with .//pip:request
.//pip:request has been compiled successfully.
textContent
As you can see, code runs fine, but the .//soapenv:Body/pip:request
XPath is not correct for the given XML, since there is no <soapenv:Body>
tag inside the given payload
element.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.