dom4j

dom4j began as a fork of the JDOM project by a developer, James Strachan, who disagreed with several aspects of the JDOM architecture including the decision to use classes instead of interfaces. dom4j has since gone its own way, and features a very different approach to a pure-Java, tree-based API than either DOM or JDOM. Notable unique features in dom4j include integrated XPath and XSLT support and optional DOM compatibility. (e.g., you can wrap a dom4j Element inside a DOM Element.)

Example 5.8 shows the dom4j version of our standard example. It’s structured pretty much like the previous two tree based APIs. First a Document object representing the XML-RPC request is constructed in memory; then serialized onto the URLConnection’s output stream. Finally, the response document is parsed to find the desired value.

Example 5.8. A dom4j based client for the Fibonacci XML-RPC server

import java.net.*;
import java.io.*;
import org.dom4j.*;
import org.dom4j.io.*;


public class Fibonaccidom4jClient {

  public final static String DEFAULT_SERVER 
   = "http://www.elharo.com/fibonacci/XML-RPC";  
  
  public static void main(String[] args) {
      
    if (args.length <= 0) {
      System.out.println(
       "Usage: java Fibonaccidom4jClient number url"
      );
      return;
    }
    
    String server = DEFAULT_SERVER;
    if (args.length >= 2) server = args[1];
      
    try {
      // Build request document
      Document request = DocumentHelper.createDocument();
      Element methodCall = request.addElement("methodCall");
      Element methodName = methodCall.addElement("methodName");
      methodName.addText("calculateFibonacci");
      Element params = methodCall.addElement("params");
      Element param = params.addElement("param");
      Element value = param.addElement("value");
      // Had to break the naming convention here because of a 
      // conflict with the Java keyword int
      Element intElement = value.addElement("int");
      intElement.addText(args[0]);
      
      // Transmit the request document
      URL u = new URL(server);
      URLConnection uc = u.openConnection();
      HttpURLConnection connection = (HttpURLConnection) uc;
      connection.setDoOutput(true);
      connection.setDoInput(true); 
      connection.setRequestMethod("POST");
      OutputStream out = connection.getOutputStream();
      
      XMLWriter serializer = new XMLWriter(out);
      serializer.write(request);
      
      out.flush();
      out.close();        

      // Read the response
      InputStream in = connection.getInputStream();
      SAXReader reader = new SAXReader();
      Document response = reader.read(in);
      in.close();
      connection.disconnect();
      
      // Use XPath to find the element we want
      Node node = response.selectSingleNode( 
       "/methodResponse/params/param/value/double" 
      );

      String result = node.getStringValue();
      System.out.println(result);
      
    }
    catch (Exception e) {
      System.err.println(e); 
    }
  
  } 

}

In dom4j the request Document object is initially created by the DocumentHelper.createDocument() factory method. The contents of the document are formed at the same time they’re added to their parent so that no nodes are ever orphaned from the tree. The serialization to the server is performed by the XMLWriter class.

Once the response has been received, dom4j parses it into a Document object using the SAXReader class that connects dom4j to an underlying parser such as Crimson or Xerces. XPath is used to extract the double element from this document. If you’re comfortable with XPath, this is a very useful and convenient feature.


Copyright 2001, 2002 Elliotte Rusty Haroldelharo@metalab.unc.eduLast Modified May 25, 2002
Up To Cafe con Leche