net.freeutils.util.config.XMLConfiguration Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of jelementary Show documentation
Show all versions of jelementary Show documentation
The Java Elementary Utilities package
The newest version!
/*
* Copyright © 2003-2024 Amichai Rothman
*
* This file is part of JElementary - the Java Elementary Utilities package.
*
* JElementary is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 2 of the License, or
* (at your option) any later version.
*
* JElementary is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with JElementary. If not, see .
*
* For additional info see https://www.freeutils.net/source/jelementary/
*/
package net.freeutils.util.config;
import java.io.*;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import org.w3c.dom.*;
/**
* The {@code XMLConfiguration} class encapsulates a configuration section
* with an XML file as the underlying implementation.
*/
public class XMLConfiguration extends Configuration {
/**
* Constructs an XMLConfiguration by parsing an XML stream.
* The encoding used is the one found in the XML header, or UTF-8 if no header exists.
*
* @param in the XML stream containing the configuration data
* @throws IOException if an error occurs
*/
public XMLConfiguration(InputStream in) throws IOException {
try {
DocumentBuilderFactory docFactory = DocumentBuilderFactory.newInstance();
DocumentBuilder docBuilder = docFactory.newDocumentBuilder();
Document doc = docBuilder.parse(in);
Element root = doc.getDocumentElement();
name = root.getTagName();
read(root, this);
} catch (Exception e) {
throw new IOException("error reading XML data", e);
} finally {
in.close();
}
}
/**
* Constructs an XMLConfiguration by parsing an XML file.
* The encoding used is the one found in the XML header, or UTF-8 if no header exists.
*
* @param filename the XML file containing the configuration data
* @throws IOException if an error occurs
*/
public XMLConfiguration(String filename) throws IOException {
this(new FileInputStream(filename));
}
/**
* Reads the given element data into the given configuration section.
*
* @param el the element to read
* @param conf the configuration section into which the data is read
* @throws IOException if an error occurs
* @throws ConfigurationException if a configuration error occurs
*/
protected static void read(Element el, Configuration conf) throws IOException, ConfigurationException {
addAttributes(el, conf);
addChildren(el, conf);
}
/**
* Adds all attributes of the given element into the given configuration section.
*
* @param el the element whose attributes are to be read
* @param conf the configuration section into which the data is read
*/
private static void addAttributes(Element el, Configuration conf) {
NamedNodeMap attributes = el.getAttributes();
if (attributes != null) {
for (int i = 0; i < attributes.getLength(); i++)
addTextNode(attributes.item(i), conf);
}
}
/**
* Adds all children of the given element into the given configuration section, recursively.
*
* @param el the element whose children are to be read
* @param conf the configuration section into which the data is read
* @throws IOException if an error occurs
*/
private static void addChildren(Element el, Configuration conf) throws IOException {
NodeList children = el.getChildNodes();
if (children == null)
return;
for (int i = 0; i < children.getLength(); i++)
addNode(children.item(i), conf);
// a text child always exists, so we remove it unless it's the
// only child, in which case it becomes the actual value
if (conf.items.size() > 1)
conf.items.remove("#text");
}
/**
* Adds the data in the given node into the given configuration section, recursively.
*
* @param n the node containing the data
* @param conf the configuration section into which the data is read
* @throws IOException if an error occurs
*/
private static void addNode(Node n, Configuration conf) throws IOException {
switch (n.getNodeType()) {
case Node.ELEMENT_NODE:
addElementNode((Element)n, conf);
break;
case Node.TEXT_NODE:
addTextNode(n, conf);
break;
// ignore comments and other types of nodes
}
}
/**
* Adds the data in the given element into the given configuration section, recursively.
*
* @param el the element containing the data
* @param conf the configuration section into which the data is read
* @throws IOException if an error occurs
*/
private static void addElementNode(Element el, Configuration conf) throws IOException {
String nodeName = el.getNodeName();
Configuration c = new Configuration(nodeName);
read(el, c);
if (c.items.size() == 1 && c.items.containsKey("#text"))
conf.add(nodeName, c.get("#text")); // only text
else
conf.add(nodeName, c); // a nested section
}
/**
* Adds the text in the given node into the given configuration section.
*
* @param n the node containing the text
* @param conf the configuration section into which the data is read
*/
private static void addTextNode(Node n, Configuration conf) {
conf.add(n.getNodeName(), n.getNodeValue());
}
}
© 2015 - 2024 Weber Informatics LLC | Privacy Policy