sascha@4070: package de.intevation.utils; sascha@4070: sascha@4070: import java.io.FileInputStream; sascha@4070: import java.io.BufferedInputStream; sascha@4070: import java.io.File; sascha@4070: import java.io.IOException; sascha@4070: import java.io.InputStream; sascha@4095: import java.io.OutputStream; sascha@4095: import java.io.StringWriter; sascha@4070: sascha@4070: import org.w3c.dom.Document; sascha@4070: sascha@4070: import javax.xml.parsers.DocumentBuilderFactory; sascha@4070: import javax.xml.parsers.ParserConfigurationException; sascha@4070: sascha@4070: import org.xml.sax.SAXException; sascha@4070: sascha@4070: import org.apache.log4j.Logger; sascha@4070: sascha@4070: import java.util.HashMap; sascha@4070: import java.util.Map; sascha@4070: sascha@4070: import javax.xml.namespace.NamespaceContext; sascha@4070: import javax.xml.namespace.QName; sascha@4070: sascha@4070: import javax.xml.xpath.XPath; sascha@4070: import javax.xml.xpath.XPathExpressionException; sascha@4070: import javax.xml.xpath.XPathFactory; sascha@4070: import javax.xml.xpath.XPathVariableResolver; sascha@4070: sascha@4083: import javax.xml.transform.Transformer; sascha@4083: import javax.xml.transform.TransformerFactory; sascha@4083: import javax.xml.transform.TransformerConfigurationException; sascha@4083: import javax.xml.transform.TransformerException; sascha@4095: import javax.xml.transform.TransformerFactoryConfigurationError; sascha@4083: sascha@4095: import javax.xml.transform.stream.StreamResult; sascha@4083: import javax.xml.transform.stream.StreamSource; sascha@4083: sascha@4083: import javax.xml.transform.dom.DOMSource; sascha@4083: import javax.xml.transform.dom.DOMResult; sascha@4083: sascha@4070: public final class XML sascha@4070: { sascha@4070: /** Logger for this class. */ sascha@4070: private static Logger log = Logger.getLogger(XML.class); sascha@4070: sascha@4070: public static class MapXPathVariableResolver teichmann@4736: implements XPathVariableResolver sascha@4070: { sascha@4070: protected Map variables; sascha@4070: sascha@4070: sascha@4070: public MapXPathVariableResolver() { sascha@4070: this.variables = new HashMap(); sascha@4070: } sascha@4070: sascha@4070: sascha@4070: public MapXPathVariableResolver(Map variables) { sascha@4070: this.variables = variables; sascha@4070: } sascha@4070: sascha@4070: sascha@4070: public void addVariable(String name, String value) { sascha@4070: variables.put(name, value); sascha@4070: } sascha@4070: sascha@4070: sascha@4070: @Override sascha@4070: public Object resolveVariable(QName variableName) { sascha@4070: String key = variableName.getLocalPart(); sascha@4070: return variables.get(key); sascha@4070: } sascha@4070: } // class MapXPathVariableResolver sascha@4070: sascha@4070: private XML() { sascha@4070: } sascha@4070: sascha@4095: /** sascha@4095: * Creates a new XML document sascha@4095: * @return the new XML document ot null if something went wrong during sascha@4095: * creation. sascha@4095: */ sascha@4095: public static final Document newDocument() { sascha@4095: DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); sascha@4095: factory.setNamespaceAware(true); sascha@4095: sascha@4095: try { sascha@4095: return factory.newDocumentBuilder().newDocument(); sascha@4095: } sascha@4095: catch (ParserConfigurationException pce) { sascha@4095: log.error(pce.getLocalizedMessage(), pce); sascha@4095: } sascha@4095: return null; sascha@4095: } sascha@4095: sascha@4070: /** sascha@4070: * Loads a XML document namespace aware from a file sascha@4070: * @param file The file to load. sascha@4070: * @return the XML document or null if something went wrong sascha@4070: * during loading. sascha@4070: */ sascha@4070: public static final Document parseDocument(File file) { sascha@4072: return parseDocument(file, Boolean.TRUE); sascha@4072: } sascha@4072: sascha@4072: public static final Document parseDocument(File file, Boolean namespaceAware) { sascha@4070: InputStream inputStream = null; sascha@4070: try { sascha@4070: inputStream = new BufferedInputStream(new FileInputStream(file)); sascha@4072: return parseDocument(inputStream, namespaceAware); sascha@4070: } sascha@4070: catch (IOException ioe) { sascha@4070: log.error(ioe.getLocalizedMessage(), ioe); sascha@4070: } sascha@4070: finally { sascha@4070: if (inputStream != null) { sascha@4070: try { inputStream.close(); } sascha@4070: catch (IOException ioe) {} sascha@4070: } sascha@4070: } sascha@4070: return null; sascha@4070: } sascha@4070: sascha@4070: sascha@4070: public static final Document parseDocument(InputStream inputStream) { sascha@4070: return parseDocument(inputStream, Boolean.TRUE); sascha@4070: } sascha@4070: sascha@4070: public static final Document parseDocument( sascha@4070: InputStream inputStream, sascha@4070: Boolean namespaceAware sascha@4070: ) { sascha@4070: DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); sascha@4070: sascha@4070: if (namespaceAware != null) { sascha@4070: factory.setNamespaceAware(namespaceAware.booleanValue()); sascha@4070: } sascha@4070: sascha@4070: try { sascha@4070: return factory.newDocumentBuilder().parse(inputStream); sascha@4070: } sascha@4070: catch (ParserConfigurationException pce) { sascha@4070: log.error(pce.getLocalizedMessage(), pce); sascha@4070: } sascha@4070: catch (SAXException se) { sascha@4070: log.error(se.getLocalizedMessage(), se); sascha@4070: } sascha@4070: catch (IOException ioe) { sascha@4070: log.error(ioe.getLocalizedMessage(), ioe); sascha@4070: } sascha@4070: return null; sascha@4070: } sascha@4070: sascha@4070: sascha@4070: /** sascha@4070: * Creates a new XPath without a namespace context. sascha@4070: * @return the new XPath. sascha@4070: */ sascha@4070: public static final XPath newXPath() { sascha@4070: return newXPath(null, null); sascha@4070: } sascha@4070: sascha@4070: /** sascha@4070: * Creates a new XPath with a given namespace context. sascha@4070: * @param namespaceContext The namespace context to be used or null sascha@4070: * if none should be used. sascha@4070: * @return The new XPath sascha@4070: */ sascha@4070: public static final XPath newXPath( sascha@4070: NamespaceContext namespaceContext, sascha@4070: XPathVariableResolver resolver) sascha@4070: { sascha@4070: XPathFactory factory = XPathFactory.newInstance(); sascha@4070: XPath xpath = factory.newXPath(); sascha@4070: if (namespaceContext != null) { sascha@4070: xpath.setNamespaceContext(namespaceContext); sascha@4070: } sascha@4070: sascha@4070: if (resolver != null) { sascha@4070: xpath.setXPathVariableResolver(resolver); sascha@4070: } sascha@4070: return xpath; sascha@4070: } sascha@4070: sascha@4070: /** sascha@4070: * Evaluates an XPath query on a given object and returns the result sascha@4070: * as a given type. No namespace context is used. sascha@4070: * @param root The object which is used as the root of the tree to sascha@4070: * be searched in. sascha@4070: * @param query The XPath query sascha@4070: * @param returnTyp The type of the result. sascha@4070: * @return The result of type 'returnTyp' or null if something sascha@4070: * went wrong during XPath evaluation. sascha@4070: */ sascha@4070: public static final Object xpath( sascha@4070: Object root, sascha@4070: String query, sascha@4070: QName returnTyp sascha@4070: ) { sascha@4070: return xpath(root, query, returnTyp, null); sascha@4070: } sascha@4070: sascha@4070: /** sascha@4070: * Evaluates an XPath query on a given object and returns the result sascha@4070: * as a given type. Optionally a namespace context is used. sascha@4070: * @param root The object which is used as the root of the tree to sascha@4070: * be searched in. sascha@4070: * @param query The XPath query sascha@4070: * @param returnType The type of the result. sascha@4070: * @param namespaceContext The namespace context to be used or null sascha@4070: * if none should be used. sascha@4070: * @return The result of type 'returnTyp' or null if something sascha@4070: * went wrong during XPath evaluation. sascha@4070: */ sascha@4070: public static final Object xpath( sascha@4070: Object root, sascha@4070: String query, sascha@4070: QName returnType, sascha@4070: NamespaceContext namespaceContext sascha@4070: ) { sascha@4070: return xpath(root, query, returnType, namespaceContext, null); sascha@4070: } sascha@4070: sascha@4070: public static final Object xpath( sascha@4070: Object root, sascha@4070: String query, sascha@4070: QName returnType, sascha@4070: NamespaceContext namespaceContext, sascha@4070: Map variables) sascha@4070: { sascha@4070: if (root == null) { sascha@4070: return null; sascha@4070: } sascha@4070: sascha@4070: XPathVariableResolver resolver = variables != null sascha@4070: ? new MapXPathVariableResolver(variables) sascha@4070: : null; sascha@4070: sascha@4070: try { sascha@4070: XPath xpath = newXPath(namespaceContext, resolver); sascha@4070: if (xpath != null) { sascha@4070: return xpath.evaluate(query, root, returnType); sascha@4070: } sascha@4070: } sascha@4070: catch (XPathExpressionException xpee) { sascha@4070: log.error(xpee.getLocalizedMessage(), xpee); sascha@4070: } sascha@4070: sascha@4070: return null; sascha@4070: } sascha@4083: sascha@4083: public static Document transform( sascha@4083: Document document, sascha@4083: File xformFile sascha@4083: ) { sascha@4083: try { sascha@4083: Transformer transformer = sascha@4083: TransformerFactory sascha@4083: .newInstance() sascha@4083: .newTransformer( sascha@4083: new StreamSource(xformFile)); sascha@4083: sascha@4083: DOMResult result = new DOMResult(); sascha@4083: sascha@4083: transformer.transform(new DOMSource(document), result); sascha@4083: sascha@4083: return (Document)result.getNode(); sascha@4083: } sascha@4083: catch (TransformerConfigurationException tce) { sascha@4083: log.error(tce, tce); sascha@4083: } sascha@4083: catch (TransformerException te) { sascha@4083: log.error(te, te); sascha@4083: } sascha@4083: sascha@4083: return null; sascha@4083: } sascha@4095: sascha@4095: /** sascha@4095: * Streams out an XML document to a given output stream. sascha@4095: * @param document The document to be streamed out. sascha@4095: * @param out The output stream to be used. sascha@4095: * @return true if operation succeeded else false. sascha@4095: */ sascha@4095: public static boolean toStream(Document document, OutputStream out) { sascha@4095: try { sascha@4095: Transformer transformer = sascha@4095: TransformerFactory.newInstance().newTransformer(); sascha@4095: DOMSource source = new DOMSource(document); sascha@4095: StreamResult result = new StreamResult(out); sascha@4095: transformer.transform(source, result); sascha@4095: return true; sascha@4095: } sascha@4095: catch (TransformerConfigurationException tce) { sascha@4095: log.error(tce.getLocalizedMessage(), tce); sascha@4095: } sascha@4095: catch (TransformerFactoryConfigurationError tfce) { sascha@4095: log.error(tfce.getLocalizedMessage(), tfce); sascha@4095: } sascha@4095: catch (TransformerException te) { sascha@4095: log.error(te.getLocalizedMessage(), te); sascha@4095: } sascha@4095: sascha@4095: return false; sascha@4095: } sascha@4095: sascha@4095: public static String toString(Document document) { sascha@4095: try { sascha@4095: Transformer transformer = sascha@4095: TransformerFactory.newInstance().newTransformer(); sascha@4095: DOMSource source = new DOMSource(document); sascha@4095: StringWriter out = new StringWriter(); sascha@4095: StreamResult result = new StreamResult(out); sascha@4095: transformer.transform(source, result); sascha@4095: out.flush(); sascha@4095: return out.toString(); sascha@4095: } sascha@4095: catch (TransformerConfigurationException tce) { sascha@4095: log.error(tce.getLocalizedMessage(), tce); sascha@4095: } sascha@4095: catch (TransformerFactoryConfigurationError tfce) { sascha@4095: log.error(tfce.getLocalizedMessage(), tfce); sascha@4095: } sascha@4095: catch (TransformerException te) { sascha@4095: log.error(te.getLocalizedMessage(), te); sascha@4095: } sascha@4095: sascha@4095: return null; sascha@4095: } sascha@4070: } sascha@4070: // vim:set ts=4 sw=4 si et sta sts=4 fenc=utf8 :