The next project, the DomainEditor application, makes several changes to the XML document that was just produced by the RssStarter application, feed.rss. The text enclosed by the link element is changed to “http://www.cadenhead.org/”, and a new item element is added:
<item>
<title>Fuzzy Zoeller Sues Over Libelous Wikipedia Page</title>
</item>
Using the nu.xom package, XML documents can be loaded into a tree from several sources: a File, InputStream, Reader, or a URL (which is specified as a String instead of a java.net.URL object).
The Builder class represents a SAX parser that can load an XML document into a Document object. Constructor methods can be used to specify a particular parser or let XOM use the first available parser from this list: Xerces 2, Crimson, Piccolo, GNU Aelfred, Oracle, XP, Saxon Aelfred, or Dom4J Aelfred. If none of these is found, the parser specified by the system property org.xml.sax.driver is used. Constructors also determine whether the parser is validating or nonvalidating.
The Builder() and Builder(true) constructors both use the default parser—most likely a version of Xerces. The presence of the Boolean argument true in the second constructor configures the parser to be validating. It would be nonvalidating otherwise. A validating parser throws a nu.xom.ValidityException if the XML document doesn’t validate according to the rules of its document type definition. The Builder object’s build() method loads an XML document from a source and returns a Document object:
Builder builder = new Builder();
File xmlFile = new File(“feed.rss”);
Document doc = builder.build(xmlFile);
These statements load an XML document from the file feed.rss barring one of two problems:
A nu.xom.ParseException is thrown if the file does not contain well-formed XML, and a java.io.IOException is thrown if the input operation fails. Elements are retrieved from the tree by calling a method of their parent node.
A Document object’s getRootElement() method returns the root element of the document:
Element root = doc.getRootElement();
In the XML document feed.rss, the root element is domains.Elements with names can be retrieved by calling their parent node’s getFirstChildElement() method with the name as a String argument:
Element channel = root.getFirstChildElement(“channel”);
This statement retrieves the channel element contained in the rss element (or null if that element could not be found). Like other examples, this is simplified by the lack of a namespace in the document; there are also methods where a name and namespace are arguments.When several elements within a parent have the same name, the parent node’s getChildElements() method can be used instead:
Elements children = channel.getChildElements()
The getChildElements() method returns an Elements object containing each of the elements. This object is a read-only list and does not change automatically if the parent node’s contents change after getChildElements() is called.
Elements has a size() method containing an integer count of the elements it holds. This can be used in a loop to cycle through each element in turn beginning with the one at position 0. There’s a get() method to retrieve each element; call it with the integer position of the element to be retrieved:
for (int i = 0; i < children.size(); i++) { Element link = children.get(i);
}