Skip to Content.
Sympa Menu

xom-interest - Re: [XOM-interest] XOM design

xom-interest AT lists.ibiblio.org

Subject: XOM API for Processing XML with Java

List archive

Chronological Thread  
  • From: Elliotte Rusty Harold <elharo AT metalab.unc.edu>
  • To: Edwin Goei <edwingo AT sun.com>
  • Cc: xom-interest AT lists.ibiblio.org
  • Subject: Re: [XOM-interest] XOM design
  • Date: Mon, 2 Dec 2002 07:44:17 -0500

At 9:38 AM -0800 11/28/02, Edwin Goei wrote:


I am comparing DOM, JDOM, DOM4J, and XOM. So I was looking over your
XOM presentation and noticed a few features of your API but no
justification for them on your site. You state:

1) DOM: Interfaces are a bad idea
DOM4J: Uses interfaces instead of classes

2) XOM does not allow method call chaining

3) JDOM: Setter methods don't return void

Could you explain why you think the above characteristics are bad in a
XML tree API?

Excellent questions. let me address them one at a time in separate messages. I'll begin with "Interfaces are a bad idea".

There are two primary and pretty much unrelated reasons XOM relies on classes rather than interfaces:

1. Interfaces (and the corresponding factory methods) are harder to use than classes (and constructors).

2. Interfaces cannot verify constraints on an object.

Allow me to elaborate.

Interfaces add an additional layer of indirection in programming. While additional layers of indirection can solve many problems, I've observed that they often lead to much confusion among programmers. A significant chunk of JDOM's ease-of-use relative to DOM comes from using classes and constructors rather than interfaces. Certainly some programmers are comfortable with this level of indirection, but I think they're a minority. They may well be the smartest and most talented programmers, but I still think they're a minority. Most programmers in my experience are much more comfortable with concrete, direct APIs.

There also interface problems that affect everyone. The biggest is that is difficult for interface-based code to determine which class it is actually using. In the ideal world, this shouldn't matter. Any implementation of the interface should be able to take the place of any other. In practice this simply isn't true. For instance, almost no DOM implementation is willing to accept or operate on nodes created by a different implementation. In my own work, I repeatedly encounter problems because TrAX loads a different XSLT processor than I was expecting. SAX is a little more stable, but I still often need to choose a particular parser rather than accepting any implementation of XMLReader. The claim of implementation independence is simply not reliable in practice. Like Java itself, programs that process XML and are based on interfaces are very much write once, test everywhere.

The second issue is even more important. Interfaces cannot verify constraints on an object. There is no way to assert in an interface that the name of an element must be a legal XML 1.0 name, or that the text content of an element cannot contain nulls and unmatched halves of surrogate pairs. You must rely on the good faith of implementers not to violate such important preconditions. My experience with DOM has taught me that this is not a sensible bet. In the DOM world, implementations routinely fail to check the constraints DOM requires them to check. Implementations routinely fail to behave as DOM requires them to behave. Sometimes this is out of ignorance. Sometimes it's a deliberate and knowing choice. Neither case is acceptable to me. If you're using XOM, you're guaranteed well-formedness, even with subclasses. I can only make that guarantee by using concrete classes that include final, non-bypassable code to check all constraints. If you can find a way to make XOM generate a non-wellformed document, even by subclassing, then it's a bug and I want to know about it so I can fix it.

Let me also address a non-issue for XOM: different implementations. The classic use-case for interfaces instead of classes is to support different implementations of the same API, multiple SAX parsers for example. In the context of XOM, this would most likely mean using a different storage backend; for instance, a native XML database instead of strings in memory. This is an interesting use-case but it is one I have chosen not to support precisely because I cannot figure out to reconcile it with the requirement that XOM guarantee well-formedness. If somebody invented a means of plugging in different storage without allowing well-formedness checks to be removed or bypassed, I'd consider it; but well-formedness comes first. If it isn't well-formed it isn't XML, and XOM is an XML API.

I also think that the proper interchange format between different systems such as a native XML database and a custom application is real XML, not a DOM object, not a XOM object, not an Infoset, but real XML. Different local contexts will have different needs. One API will not suit them all. We can let a thousand incompatible APIs bloom, as long they all talk to each other by sending and receiving well-formed XML. On the other hand, subsetting or supersetting XML is an interoperability disaster. It is precisely this that XOM's draconian focus on well-formedness is designed to avoid.
--

+-----------------------+------------------------+-------------------+
| Elliotte Rusty Harold | elharo AT metalab.unc.edu | Writer/Programmer |
+-----------------------+------------------------+-------------------+
| XML in a Nutshell, 2nd Edition (O'Reilly, 2002) |
| http://www.cafeconleche.org/books/xian2/ |
| http://www.amazon.com/exec/obidos/ISBN%3D0596002920/cafeaulaitA/ |
+----------------------------------+---------------------------------+
| Read Cafe au Lait for Java News: http://www.cafeaulait.org/ |
| Read Cafe con Leche for XML News: http://www.cafeconleche.org/ |
+----------------------------------+---------------------------------+




Archive powered by MHonArc 2.6.24.

Top of Page