javaxt.xml.DOM Maven / Gradle / Ivy
package javaxt.xml;
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.InputStream;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
//imports used to transform xml
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.dom.DOMSource;
import javax.xml.transform.stream.StreamResult;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.NamedNodeMap;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
//******************************************************************************
//** DOM Utilities - By Peter Borissow
//******************************************************************************
/**
* Provides basic utilities to simplify loading and parsing xml
*
******************************************************************************/
public class DOM {
// **************************************************************************
// ** Private Constructor
// **************************************************************************
/** Defeats Instantiation */
private DOM() {
}
// **************************************************************************
// ** createDocument
// **************************************************************************
/** Used to create a DOM document from a URL. */
public static Document createDocument(java.net.URL url) {
return new javaxt.http.Request(url).getResponse().getXML();
}
// **************************************************************************
// ** createDocument
// **************************************************************************
/**
* Used to create a DOM document from a java.io.File. Returns null if the
* file cannot be serialized to XML.
*/
public static Document createDocument(java.io.File file) {
if (file.exists() == false)
return null;
try {
return createDocument(new java.io.FileInputStream(file));
} catch (Exception e) {
// e.printStackTrace();
return null;
}
}
// **************************************************************************
// ** createDocument
// **************************************************************************
/**
* Used to create a DOM document from a String. Returns null if the string
* is invalid.
*/
public static Document createDocument(String xml) {
if (xml == null)
return null;
xml = xml.trim();
String encoding = "UTF-8";
try {
String xmlHeader = xml.substring(xml.indexOf(""), xml.indexOf("?>"));
if (xmlHeader.contains(" encoding")) {
encoding = xmlHeader.substring(xmlHeader.indexOf(" encoding") + " encoding".length());
encoding = encoding.substring(encoding.indexOf("=") + 1);
while (encoding.substring(0, 1).equals(" ")) {
encoding = encoding.substring(1);
}
String firstChar = encoding.substring(0, 1);
if (firstChar.equals("\"") || firstChar.equals("'")) {
encoding = encoding.substring(1);
encoding = encoding.substring(0, encoding.indexOf(firstChar)).trim();
} else {
encoding = encoding.substring(0, encoding.indexOf(" ")).trim();
}
}
} catch (Exception e) {
}
return createDocument(xml, encoding);
}
public static Document createDocument(String xml, String charsetName) {
xml = xml.trim();
try {
return createDocument(new ByteArrayInputStream(xml.getBytes(charsetName)));
} catch (Exception e) {
// e.printStackTrace();
return createDocument(new ByteArrayInputStream(xml.getBytes()));
}
}
// **************************************************************************
// ** createDocument
// **************************************************************************
/** Used to create a DOM document from an InputStream. */
public static Document createDocument(InputStream is) {
try {
DocumentBuilderFactory builderFactory = DocumentBuilderFactory.newInstance();
DocumentBuilder builder = builderFactory.newDocumentBuilder();
return builder.parse(is);
} catch (Exception e) {
// e.printStackTrace();
return null;
}
}
// **************************************************************************
// ** getOuterNode
// **************************************************************************
/**
* Returns the outer node for a given xml document.
*
* @param xml
* A org.w3c.dom.Document
*/
public static Node getOuterNode(Document xml) {
if (xml == null)
return null;
NodeList OuterNodes = xml.getChildNodes();
for (int i = 0; i < OuterNodes.getLength(); i++) {
if (OuterNodes.item(i).getNodeType() == 1) {
return OuterNodes.item(i);
}
}
return null;
}
// **************************************************************************
// ** equals
// **************************************************************************
/**
* Used to compare two XML documents by performing a raw string comparison.
*/
public static boolean equals(Document xml, Document xml2) {
if (xml == null && xml2 == null)
return true;
if (xml != null && xml2 == null)
return false;
if (xml == null && xml2 != null)
return false;
return getText(xml).equals(getText(xml2));
}
// **************************************************************************
// ** getText
// **************************************************************************
/**
* Converts a DOM Document to a String
*
* @param xml
* A org.w3c.dom.Document
*/
public static String getText(Document xml) {
try {
TransformerFactory factory = TransformerFactory.newInstance();
Transformer transformer = factory.newTransformer();
DOMSource source = new DOMSource(xml);
ByteArrayOutputStream bas = new ByteArrayOutputStream();
StreamResult result = new StreamResult(bas);
transformer.transform(source, result);
String encoding = xml.getXmlEncoding();
if (encoding != null)
return bas.toString(encoding);
else
return bas.toString();
} catch (Exception e) {
// System.out.println(e.toString());
return "";
}
}
// **************************************************************************
// ** getText
// **************************************************************************
/** Converts a NodeList to a String */
public static String getText(NodeList nodeList) {
StringBuffer ret = new StringBuffer();
for (int i = 0; i < nodeList.getLength(); i++) {
ret.append(getText(nodeList.item(i)));
}
return ret.toString();
}
// **************************************************************************
// ** getText
// **************************************************************************
/** Converts a Node to a String */
public static String getText(Node node) {
StringBuffer ret = new StringBuffer();
if (node.getNodeType() == 1) {
if (hasChildren(node)) {
ret.append(getNodeValue(node));
} else {
ret.append("<" + node.getNodeName() + getAttributes(node) + ">");
ret.append(getNodeValue(node));
ret.append("" + node.getNodeName() + ">");
}
}
return ret.toString();
}
// **************************************************************************
// ** getAttributes
// **************************************************************************
/** Used to retrieve all of the attributes for a given node. */
private static String getAttributes(Node node) {
if (node == null)
return "";
NamedNodeMap attr = node.getAttributes();
String Attributes = "";
if (attr != null) {
for (int j = 0; j < attr.getLength(); j++) {
String name = attr.item(j).getNodeName();
String value = attr.item(j).getTextContent();
if (value == null)
value = attr.item(j).getNodeValue();
if (value == null)
value = "";
// System.out.println(name + "=" + attr.item(j).getNodeValue());
Attributes += " " + name + "=\"" + value + "\"";
}
}
return Attributes;
}
// **************************************************************************
// ** hasChildren
// **************************************************************************
/**
* Used to determine whether a given node has any children. Differs from the
* native DOM implementation in that this function only considers child
* nodes that have a node type value equal to 1.
*/
public static boolean hasChildren(Node node) {
NodeList nodeList = node.getChildNodes();
for (int i = 0; i < nodeList.getLength(); i++) {
if (nodeList.item(i).getNodeType() == 1) {
return true;
}
}
return false;
}
// **************************************************************************
// ** getAttributeValue
// **************************************************************************
/**
* Used to return the value of a given node attribute. The search is case
* insensitive. If no match is found, returns an empty string.
*/
public static String getAttributeValue(NamedNodeMap attrCollection, String attrName) {
if (attrCollection != null) {
for (int i = 0; i < attrCollection.getLength(); i++) {
Node node = attrCollection.item(i);
if (node.getNodeName().equalsIgnoreCase(attrName)) {
return node.getNodeValue();
}
}
}
return "";
}
// **************************************************************************
// ** getAttributeValue
// **************************************************************************
/**
* Used to return the value of a given node attribute. The search is case
* insensitive. If no match is found, returns an empty string.
*/
public static String getAttributeValue(Node node, String attrName) {
return getAttributeValue(node.getAttributes(), attrName);
}
// **************************************************************************
// ** setAttributeValue
// **************************************************************************
/**
* Used to create or update an attribute.
*/
public static void setAttributeValue(Node node, String attrName, String attrValue) {
if (node == null)
return;
try {
((Element) node).setAttribute(attrName, attrValue);
} catch (Exception e) {
// Apparently some nodes can't be cast to an Element so we can try
// to update the node's attribute collection.
try {
NamedNodeMap attrCollection = node.getAttributes();
for (int i = 0; i < attrCollection.getLength(); i++) {
org.w3c.dom.Node attribute = attrCollection.item(i);
if (attribute.getNodeName().equals(attrName)) {
attribute.setNodeValue(attrValue);
return;
}
}
// TODO: If we're still here, create new attribute
} catch (Exception ex) {
}
}
}
// **************************************************************************
// ** getNodeValue
// **************************************************************************
/**
* Returns the value of a given node as text. If the node has children, the
* method will return an xml fragment which will include the input node as
* the outer node. This is a legacy feature which should be deprecated over
* time.
*/
public static String getNodeValue(Node node) {
String nodeValue = "";
if (hasChildren(node)) {
StringBuffer xmlTree = new StringBuffer();
traverse(node, xmlTree);
nodeValue = xmlTree.toString();
} else {
nodeValue = node.getTextContent();
}
if (nodeValue == null) {
return "";
} else {
return nodeValue;
}
}
private static void traverse(Node tree, StringBuffer xmlTree) {
if (tree.getNodeType() == 1) {
String Attributes = getAttributes(tree);
xmlTree.append("<" + tree.getNodeName() + Attributes + ">");
if (hasChildren(tree)) {
NodeList xmlNodeList = tree.getChildNodes();
for (int i = 0; i < xmlNodeList.getLength(); i++) {
traverse(xmlNodeList.item(i), xmlTree);
}
} else {
String nodeValue = tree.getTextContent();
if (nodeValue == null) {
nodeValue = "";
}
xmlTree.append(nodeValue);
}
xmlTree.append("" + tree.getNodeName() + ">");
}
}
// **************************************************************************
// ** getDocumentAttributes
// **************************************************************************
/**
* @param xml
* A org.w3c.dom.Document
*/
public static NamedNodeMap getDocumentAttributes(Document xml) {
NodeList Definitions = xml.getChildNodes();
for (int i = 0; i < Definitions.getLength(); i++) {
if (Definitions.item(i).getNodeType() == 1) {
return Definitions.item(i).getAttributes();
}
}
return null;
}
// **************************************************************************
// ** getTargetNameSpace
// **************************************************************************
/**
* Returns the "targetNamespace" for a given xml document.
*
* @param xml
* A org.w3c.dom.Document
*/
public static String getTargetNameSpace(Document xml) {
NamedNodeMap attr = getDocumentAttributes(xml);
return getAttributeValue(attr, "targetNamespace");
}
// **************************************************************************
// ** getNameSpaces
// **************************************************************************
/**
* Returns a hashmap with all the namespaces found in a given xml document.
* The hashmap key is the namespace prefix and the corresponding value is
* the namespace url.
*
* @param xml
* A org.w3c.dom.Document
*/
public static java.util.HashMap getNameSpaces(Document xml) {
java.util.HashMap namespaces = new java.util.HashMap();
getNameSpaces(getOuterNode(xml), namespaces);
return namespaces;
}
private static void getNameSpaces(Node node, java.util.HashMap namespaces) {
if (node.getNodeType() == 1) {
NamedNodeMap attr = node.getAttributes();
if (attr != null) {
for (int j = 0; j < attr.getLength(); j++) {
String name = attr.item(j).getNodeName();
String value = attr.item(j).getTextContent();
if (name.startsWith("xmlns:")) {
name = name.substring(6);
namespaces.put(name, value);
}
}
}
if (hasChildren(node)) {
NodeList childNodes = node.getChildNodes();
for (int i = 0; i < childNodes.getLength(); i++) {
getNameSpaces(childNodes.item(i), namespaces);
}
}
}
}
// **************************************************************************
// ** getElementsByTagName
// **************************************************************************
/**
* Returns an array of nodes that match a given tagName (node name). The
* results will include all nodes that match, regardless of namespace. To
* narrow the results to a specific namespace, simply include the namespace
* prefix in the tag name (e.g. "t:Contact").
*/
public static org.w3c.dom.Node[] getElementsByTagName(String tagName, Document xml) {
return getElementsByTagName(tagName, getOuterNode(xml));
}
// **************************************************************************
// ** getElementsByTagName
// **************************************************************************
/**
* Returns an array of nodes that match a given tagName (node name). The
* results will include all nodes that match, regardless of namespace. To
* narrow the results to a specific namespace, simply include the namespace
* prefix in the tag name (e.g. "t:Contact"). Returns an empty array if no
* nodes are found.
*/
public static org.w3c.dom.Node[] getElementsByTagName(String tagName, Node node) {
java.util.ArrayList nodes = new java.util.ArrayList();
getElementsByTagName(tagName, node, nodes);
return nodes.toArray(new org.w3c.dom.Node[nodes.size()]);
}
private static void getElementsByTagName(String tagName, Node node, java.util.ArrayList nodes) {
if (node != null && node.getNodeType() == 1) {
String nodeName = node.getNodeName().trim();
if (nodeName.contains(":") && !tagName.contains(":")) {
nodeName = nodeName.substring(nodeName.indexOf(":") + 1);
}
if (nodeName.equalsIgnoreCase(tagName)) {
nodes.add(node);
}
if (hasChildren(node)) {
NodeList childNodes = node.getChildNodes();
for (int i = 0; i < childNodes.getLength(); i++) {
getElementsByTagName(tagName, childNodes.item(i), nodes);
}
}
}
}
/** Converts a NodeList into an array to simplify nested loops. */
public static Node[] getNodes(NodeList nodeList) {
java.util.ArrayList nodes = new java.util.ArrayList();
for (int i = 0; i < nodeList.getLength(); i++) {
Node node = nodeList.item(i);
if (node.getNodeType() == 1)
nodes.add(node);
}
return nodes.toArray(new Node[nodes.size()]);
}
public final static String ESCAPE_CHARS = "<>&\"\'";
public final static java.util.List ESCAPE_STRINGS = java.util.Collections
.unmodifiableList(java.util.Arrays.asList(new String[] { "<", ">", "&", """, "'" }));
private static String UNICODE_LOW = "" + ((char) 0x20); // space
private static String UNICODE_HIGH = "" + ((char) 0x7f);
// **************************************************************************
// ** escapeXml
// **************************************************************************
/**
* Used to encode text data for use in an XML tag or attribute.
*/
public static String escapeXml(String content) {
String result = content;
if ((content != null) && (content.length() > 0)) {
boolean modified = false;
StringBuilder stringBuilder = new StringBuilder(content.length());
for (int i = 0, count = content.length(); i < count; ++i) {
String character = content.substring(i, i + 1);
int pos = ESCAPE_CHARS.indexOf(character);
if (pos > -1) {
stringBuilder.append(ESCAPE_STRINGS.get(pos));
modified = true;
} else {
if ((character.compareTo(UNICODE_LOW) > -1) && (character.compareTo(UNICODE_HIGH) < 1)) {
stringBuilder.append(character);
} else {
stringBuilder.append("" + ((int) character.charAt(0)) + ";");
modified = true;
}
}
}
if (modified) {
result = stringBuilder.toString();
}
}
return result;
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy